<HTML>
<HEAD>
<TITLE>



    C++ Standard Core Language
    
      Defect Reports
     </TITLE>
</HEAD>
<BODY>
<TABLE ALIGN="RIGHT" CELLSPACING="0" CELLPADDING="0">
<TR>
<TD ALIGN="RIGHT">
      Document number:
     </TD><TD>
        &nbsp;J16/07-0023 = WG21 N2163</TD>
</TR>
<TR>
<TD ALIGN="RIGHT">
      Date:
     </TD><TD>
      &nbsp;2007-01-14</TD>
</TR>
<TR>
<TD ALIGN="RIGHT">
      Project:
     </TD><TD>
      &nbsp;Programming Language C++
     </TD>
</TR>
<TR>
<TD ALIGN="RIGHT">
      Reference:
     </TD><TD>
      &nbsp;ISO/IEC IS 14882:2003
     </TD>
</TR>
<TR>
<TD ALIGN="RIGHT">
      Reply to:
     </TD><TD>
      &nbsp;William M. Miller
     </TD>
</TR>
<TR>
<TD></TD><TD>
      &nbsp;Edison Design Group, Inc.
     </TD>
</TR>
<TR>
<TD></TD><TD>
      &nbsp;<TT>wmm@edg.com</TT></TD>
</TR>
</TABLE>
<BR CLEAR="ALL">
<BR>
<CENTER>
<H2>



     C++ Standard Core Language
     
       Defect Reports,
      



     Revision
     45</H2>
</CENTER>
<BR>
<P>
      This document contains the C++ core language issues that have been
      categorized as Defect Reports by the Committee (J16 +
      WG21), that is, issues with status
      "<A HREF="#DR Status">DR</A>,"
      "<A HREF="#WP Status">WP</A>," and
      "<A HREF="#TC1 Status">TC1</A>,"
      along with their proposed resolutions.  <B>ONLY RESOLUTIONS FOR
      ISSUES WITH TC1 STATUS ARE PART OF THE INTERNATIONAL STANDARD
      FOR C++.</B> The other issues are provided for informational
      purposes only, as an indication of the intent of the Committee.
      They should not be considered definitive until or unless they
      appear in an approved Technical Corrigendum or revised
      International Standard for C++.
     </P>
<P>
    This document is part of a group of related documents that
    together describe the issues that have been raised regarding the
    C++ Standard.  The other documents in the group are:
   </P>
<UL>
<LI>
<A HREF="cwg_active.html">Active Issues List</A>, which contains
      explanatory material for the entire document group and a list of
      the issues that have not yet been acted upon by the Committee.
     </LI>
<LI>
<A HREF="cwg_closed.html">Closed Issues List</A>, which contains
      the issues which the Committee has decided are not defects
      in the International Standard, including a brief rationale
      explaining the reason for the decision.
     </LI>
<LI>
<A HREF="cwg_toc.html">Table of Contents</A>, which contains a
     summary listing of all issues in numerical order.
    </LI>
<LI>
<A HREF="cwg_index.html">Index by Section</A>, which contains a
     summary listing of all issues arranged in the order of the
     sections of the Standard with which they deal most directly.
    </LI>
<LI>
<A HREF="cwg_status.html">Index by Status</A>, which contains a
     summary listing of all issues grouped by status.
    </LI>
</UL>
<P>
     For more information, including a description of the meaning of
     the issue status codes and instructions on reporting new issues,
     please see <A HREF="cwg_active.html">the Active Issues List</A>.
    </P>
<HR>
<A NAME="DR Status"></A>
<H3>Issues with "DR" Status</H3>
<HR>
<A NAME="505"></A>
<H4>505.
  
Conditionally-supported behavior for unknown character escapes
</H4>
<B>Section: </B>2.13.2&nbsp;



 <A HREF="lex.html#lex.ccon">lex.ccon</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>DR
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>14 Apr 2005<BR>


<P>[Voted into WP at the October, 2006 meeting.]</P>

<P>The current wording of 2.13.2&nbsp;



 <A HREF="lex.html#lex.ccon">lex.ccon</A> paragraph 3
states,</P>

<BLOCKQUOTE>

If the character following a backslash is not one of those specified,
the behavior is undefined.

</BLOCKQUOTE>

<P>Paper J16/04-0167=WG21 N1727 suggests that such character escapes
be ill-formed.  In discussions at the Lillehammer meeting, however,
the CWG felt that the newly-approved category of
conditionally-supported behavior would be more appropriate.</P>

<P>
<B>Proposed resolution (April, 2006):</B>
</P>

<P>Change the next-to-last sentence of 2.13.2&nbsp;



 <A HREF="lex.html#lex.ccon">lex.ccon</A>
paragraph 3 from:</P>

<BLOCKQUOTE>

If the character following a backslash is not one of those specified,
the behavior is undefined.

</BLOCKQUOTE>

<P>to:</P>

<BLOCKQUOTE>

Escape sequences in which the character following the backslash is not
listed in Table 6 are conditionally-supported, with
implementation-defined semantics.

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="514"></A>
<H4>514.
  
Is the initializer for a namespace member in the scope of the namespace?
</H4>
<B>Section: </B>3.4.1&nbsp;



 <A HREF="basic.html#basic.lookup.unqual">basic.lookup.unqual</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>DR
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>24 Mar 2005<BR>


<P>[Voted into WP at the October, 2006 meeting.]</P>

<P>Is the following code well-formed?</P>

<PRE>
    namespace N {
      int i;
      extern int j;
    }
    int N::j = i;
</PRE>

<P>The question here is whether the lookup for <TT>i</TT> in the
initializer of <TT>N::j</TT> finds the declaration in namespace
<TT>N</TT> or not.  Implementations differ on this question.</P>

<P>If <TT>N::j</TT> were a static data member of a class, the
answer would be clear: both 3.4.1&nbsp;



 <A HREF="basic.html#basic.lookup.unqual">basic.lookup.unqual</A>
paragraph 12 and 8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A> paragraph 11 say that
the initializer &ldquo;is in the scope of the member's
class.&rdquo;  There is no such provision for namespace
members defined outside the namespace, however.</P>

<P>The reasoning given in 3.4.1&nbsp;



 <A HREF="basic.html#basic.lookup.unqual">basic.lookup.unqual</A> may be
instructive:</P>

<BLOCKQUOTE>

A name used in the definition of a <TT>static</TT> data member of
class <TT>X</TT> (9.4.2&nbsp;



 <A HREF="class.html#class.static.data">class.static.data</A>) (after the
<I>qualified-id</I> of the static member) is looked up as if the name
was used in a member function of <TT>X</TT>.

</BLOCKQUOTE>

<P>It is certainly the case that a name used in a function that is
a member of a namespace is looked up in that namespace
(3.4.1&nbsp;



 <A HREF="basic.html#basic.lookup.unqual">basic.lookup.unqual</A> paragraph 6), regardless of whether
the definition is inside or outside that namespace.  Initializers
for namespace members should probably be looked up the same way.</P>

<P>
<B>Proposed resolution (April, 2006):</B>
</P>

<P>Add a new paragraph following 3.4.1&nbsp;



 <A HREF="basic.html#basic.lookup.unqual">basic.lookup.unqual</A>
paragraph 12:</P>

<BLOCKQUOTE>

<P>If a variable member of a namespace is defined outside of the scope
of its namespace then any name used in the definition of the variable
member (after the <I>declarator-id</I>) is looked up as if the
definition of the variable member occurred in its
namespace. [<I>Example:</I>
</P>

<PRE>
    namespace N {
      int i = 4;
      extern int j;
    }

    int i = 2;

    int N::j = i;	//<SPAN STYLE="font-family:Times"> <TT>N::j</TT><I> == 4</I></SPAN>
</PRE>

<P>&mdash;<I>end example</I>]</P>

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="557"></A>
<H4>557.
  
Does argument-dependent lookup cause template instantiation?
</H4>
<B>Section: </B>3.4.2&nbsp;



 <A HREF="basic.html#basic.lookup.argdep">basic.lookup.argdep</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>DR
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>8 February 2006<BR>


<P>[Voted into WP at the October, 2006 meeting.]</P>

<P>One might assume from 14.7.1&nbsp;



 <A HREF="template.html#temp.inst">temp.inst</A> paragraph 1
that argument-dependent lookup would require instantiation of any
class template specializations used in argument types:</P>

<BLOCKQUOTE>

Unless a class template specialization has been explicitly
instantiated (14.7.2&nbsp;



 <A HREF="template.html#temp.explicit">temp.explicit</A>) or explicitly specialized
(14.7.3&nbsp;



 <A HREF="template.html#temp.expl.spec">temp.expl.spec</A>), the class template specialization is
implicitly instantiated when the specialization is referenced in a
context that requires a completely-defined object type or when the
completeness of the class type affects the semantics of the program.

</BLOCKQUOTE>

<P>A complete class type is required to determine the associated
classes and namespaces for the argument type (to determine the class's
bases) and to determine the friend functions declared by the class, so
the completeness of the class type certainly &ldquo;affects the
semantics of the program.&rdquo;</P>

<P>This conclusion is reinforced by the second bullet of
3.4.2&nbsp;



 <A HREF="basic.html#basic.lookup.argdep">basic.lookup.argdep</A> paragraph 2:</P>

<UL>
<LI>
<P>If <TT>T</TT> is a class type (including unions), its associated
classes are: the class itself; the class of which it is a member, if
any; and its direct and indirect base classes. Its associated
namespaces are the namespaces in which its associated classes are
defined.</P>
</LI>
</UL>

<P>A class template specialization is a class type, so the second
bullet would appear to apply, requiring the specialization to be
instantiated in order to determine its base classes.</P>

<P>However, bullet 8 of that paragraph deals explicitly with class
template specializations:</P>

<UL>
<LI>
<P>If <TT>T</TT> is a class template specialization its
associated namespaces and classes are the namespace in which the
template is defined; for member templates, the member template&rsquo;s
class; the namespaces and classes associated with the types of the
template arguments provided for template type parameters (excluding
template template parameters); the namespaces in which any template
template arguments are defined; and the classes in which any member
templates used as template template arguments are
defined.</P>
</LI>
</UL>

<P>Note that the class template specialization itself is <I>not</I>
listed as an associated class, unlike other class types, and there is
no mention of base classes.  If bullet 8 were intended as a supplement
to the treatment of class types in bullet 2, one would expect phrasing
along the lines of, &ldquo;In addition to the associated namespaces
and classes for all class types...&rdquo; or some such; instead,
bullet 8 reads like a self-contained and complete specification.</P>

<P>If argument-dependent lookup does not cause implicit
instantiation, however, examples like the following fail:</P>

<PRE>
    template &lt;typename T&gt; class C {
        friend void f(C&lt;T&gt;*) { }
    };
    void g(C&lt;int&gt;* p) {
        f(p);    // found by ADL??
    }
</PRE>

<P>Implementations differ in whether this example works or not.</P>

<P>
<B>Proposed resolution (April, 2006):</B>
</P>

<OL>

<LI>
<P>Change bullet 2 of 3.4.2&nbsp;



 <A HREF="basic.html#basic.lookup.argdep">basic.lookup.argdep</A> paragraph 2
as indicated:</P>

<UL>
<LI>
<P>

If <TT>T</TT> is a class type (including unions), its associated
classes are: the class itself; the class of which it is a member, if
any; and its direct and indirect base classes. Its associated
namespaces are the namespaces <S>in</S> <B>of</B> which its associated
classes are <S>defined</S> <B>members</B>.  <B>Furthermore,
if <TT>T</TT> is a class template specialization, its associated
namespaces and classes also include: the namespaces and classes
associated with the types of the template arguments provided for
template type parameters (excluding template template parameters); the
namespaces of which any template template arguments are members; and
the classes of which any member templates used as template template
arguments are members. [<I>Note:</I> Non-type template arguments do not
contribute to the set of associated namespaces.  &mdash;<I>end
note</I>]</B>

</P>
</LI>
</UL>

</LI>

<LI>
<P>Delete bullet 8 of 3.4.2&nbsp;



 <A HREF="basic.html#basic.lookup.argdep">basic.lookup.argdep</A> paragraph 2:</P>

<UL>
<S>
<LI>
<P>

If <TT>T</TT> is a class template specialization its associated
namespaces and classes are the namespace in which the template is
defined; for member templates, the member template&rsquo;s class; the
namespaces and classes associated with the types of the template
arguments provided for template type parameters (excluding template
template parameters); the namespaces in which any template template
arguments are defined; and the classes in which any member templates
used as template template arguments are defined. [<I>Note:</I> non-type
template arguments do not contribute to the set of associated
namespaces. &mdash;<I>end note</I>]

</P>
</LI>
</S>
</UL>

</LI>

</OL>

<BR>
<BR>
<HR>
<A NAME="305"></A>
<H4>305.
  
Name lookup in destructor call
</H4>
<B>Section: </B>3.4.5&nbsp;



 <A HREF="basic.html#basic.lookup.classref">basic.lookup.classref</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>DR
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mark Mitchell
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>19 May 2001<BR>


<P>[Voted into WP at the October, 2006 meeting.]</P>

<P>I believe this program is invalid:
<PRE>
    struct A {
    };

    struct C {
      struct A {};
      void f ();
    };

    void C::f () {
      ::A *a;
      a-&gt;~A ();
    }
</PRE>
The problem is that 3.4.5&nbsp;



 <A HREF="basic.html#basic.lookup.classref">basic.lookup.classref</A> says that you have to look
up <TT>A</TT> in both the context of the pointed-to-type (i.e.,
<TT>::A</TT>), and
in the context of the postfix-expression (i.e., the body of <TT>C::f</TT>), and
that if the name is found in both places it must name the same type in
both places.</P>

<P>The EDG front end does not issue an error about this program, though.</P>

<P>Am I reading the standardese incorrectly?</P>

<P>
<U>John Spicer</U>: I think you are reading it correctly.  I think
I've been hoping that this would
get changed.  Unlike other dual lookup contexts, this is one in which the
compiler already knows the right answer (the type must match that of the left
hand of the <TT>-&gt;</TT> operator).  So I think that if either of the types
found matches
the one required, it should be sufficient.  You can't say <TT>a-&gt;~::A()</TT>,
which
means you are forced to say <TT>a-&gt;::A::~A()</TT>, which disables the virtual
mechanism.  So you would have to do something like create a local typedef
for the desired type.</P>

<P>See also issues <A HREF="
     cwg_defects.html#244">244</A>,
<A HREF="
     cwg_active.html#399">399</A>, and
<A HREF="
     cwg_defects.html#466">466</A>.</P>

<P>
<B>Proposed resolution (April, 2006):</B>
</P>

<OL>

<LI>
<P>Remove the indicated text from 3.4.5&nbsp;



 <A HREF="basic.html#basic.lookup.classref">basic.lookup.classref</A>
paragraph 2:</P>

<BLOCKQUOTE>

If the <I>id-expression</I> in a class member access (5.2.5&nbsp;



 <A HREF="expr.html#expr.ref">expr.ref</A>) is an <I>unqualified-id</I>, and the type of the
object expression is of a class type <TT>C</TT> <S>(or of pointer to a
class type <TT>C</TT>)</S>, the <I>unqualified-id</I> is looked up in
the scope of class <TT>C</TT>...

</BLOCKQUOTE>

</LI>

<LI>
<P>Change 3.4.5&nbsp;



 <A HREF="basic.html#basic.lookup.classref">basic.lookup.classref</A> paragraph 3 as indicated:</P>

<BLOCKQUOTE>

If the <I>unqualified-id</I> is <TT>~</TT><I>type-name</I>,
<B>the <I>type-name</I> is looked up in the context of the entire
<I>postfix-expression</I>.</B> <S>and</S> <B>If</B> the
type <B><TT>T</TT></B> of the object expression is of a class
type <TT>C</TT> <S>(or of pointer to a class type <TT>C</TT>)</S>,
the <I>type-name</I> is <B>also</B> looked up <S>in the context of the
entire <I>postfix-expression</I> and</S> in the scope of
class <TT>C</TT>. <S>The <I>type-name</I> shall refer to
a <I>class-name</I>. If <I>type-name</I> is found in both contexts,
the name shall refer to the same class type. If the type of the object
expression is of scalar type, the <I>type-name</I> is looked up in the
scope of the complete <I>postfix-expression</I>.</S> <B>At least one
of the lookups shall find a name that refers to (possibly
cv-qualified)
<TT>T</TT>.  [<I>Example:</I>

<PRE>
    struct A { };

    struct B {
      struct A { };
      void f(::A* a);
    };

    void B::f(::A* a) {
      a-&gt;~A();  //<SPAN STYLE="font-family:Times"><I> OK, lookup in </I><TT>*a</TT><I> finds the injected-class-name</I></SPAN>
    }
</PRE>

&mdash;<I>end example</I>]</B>

</BLOCKQUOTE>

</LI>
</OL>

<P>
<I>[Note: this change also resolves <A HREF="
     cwg_defects.html#414">issue 414</A>.]</I>
</P>

<BR>
<BR>
<HR>
<A NAME="414"></A>
<H4>414.
  
Multiple types found on destructor lookup
</H4>
<B>Section: </B>3.4.5&nbsp;



 <A HREF="basic.html#basic.lookup.classref">basic.lookup.classref</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>DR
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>John Spicer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>1 May 2003<BR>


<P>[Voted into WP at the October, 2006 meeting.]</P>

<P>By 3.4.5&nbsp;



 <A HREF="basic.html#basic.lookup.classref">basic.lookup.classref</A> paragraph 3, the following is
ill-formed because the two lookups of the destructor name (in
the scope of the class of the object and in the surrounding
context) find different Xs:</P>
<PRE>
  struct X {};
  int main() {
    X x;
    struct X {};
    x.~X();  // Error?
  }
</PRE>
<P>This is silly, because the compiler knows what the type has
to be, and one of the things found matches that.  The lookup
should require only that one of the lookups finds the required
class type.</P>

<P>
<B>Proposed resolution (April, 2005):</B>
</P>

<P>This issue is resolved by the resolution of <A HREF="
     cwg_defects.html#305">issue 305</A>.</P>

<BR>
<BR>
<HR>
<A NAME="521"></A>
<H4>521.
  
Requirements for exceptions thrown by allocation functions
</H4>
<B>Section: </B>3.7.3.1&nbsp;



 <A HREF="basic.html#basic.stc.dynamic.allocation">basic.stc.dynamic.allocation</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>DR
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Alisdair Meredith
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>22 May 2005<BR>


<P>[Voted into WP at the October, 2006 meeting.]</P>

<P>According to 3.7.3.1&nbsp;



 <A HREF="basic.html#basic.stc.dynamic.allocation">basic.stc.dynamic.allocation</A> paragraph 3,</P>

<BLOCKQUOTE>

Any other allocation function that fails to allocate storage shall
only indicate failure by throwing an exception of
class <TT>std::bad_alloc</TT> (18.4.2.1&nbsp;



 <A HREF="lib-support.html#lib.bad.alloc">lib.bad.alloc</A>) or a
class derived from <TT>std::bad_alloc</TT>.

</BLOCKQUOTE>

<P>Shouldn't this statement have the usual requirements for an
unambiguous and accessible base class?</P>

<P>
<B>Proposed resolution (April, 2006):</B>
</P>

<P>Change the last sentence of 3.7.3.1&nbsp;



 <A HREF="basic.html#basic.stc.dynamic.allocation">basic.stc.dynamic.allocation</A>
paragraph 3 as indicated:</P>

<BLOCKQUOTE>

Any other allocation function that fails to allocate storage shall
<S>only</S> indicate failure <B>only</B> by throwing an exception of
<S>class <TT>std::bad_alloc</TT> (18.4.2.1&nbsp;



 <A HREF="lib-support.html#lib.bad.alloc">lib.bad.alloc</A>) or a
class derived from <TT>std::bad_alloc</TT></S> <B>a type that would
match a handler (15.3&nbsp;



 <A HREF="except.html#except.handle">except.handle</A>) of type
<TT>std::bad_alloc</TT> (18.4.2.1&nbsp;



 <A HREF="lib-support.html#lib.bad.alloc">lib.bad.alloc</A>)</B>.

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="480"></A>
<H4>480.
  
Is a base of a virtual base also virtual?
</H4>
<B>Section: </B>4.11&nbsp;



 <A HREF="conv.html#conv.mem">conv.mem</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>DR
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mark Mitchell
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>18 Oct 2004<BR>


<P>[Voted into WP at the October, 2006 meeting.]</P>

<P>When the Standard refers to a virtual base class, it should be
understood to include base classes of virtual bases.  However,
the Standard doesn't actually say this anywhere, so when
4.11&nbsp;



 <A HREF="conv.html#conv.mem">conv.mem</A> (for example) forbids casting to a
derived class member pointer from a virtual base class member
pointer, it could be read as meaning:</P>

<PRE>
  struct B {};
  struct D : public B {};
  struct D2 : virtual public D {};

  int B::*p;
  int D::*q;

  void f() {
    static_cast&lt;int D2::*&gt;(p);  // <SPAN STYLE="font-family:Times"><I>permitted</I></SPAN>
    static_cast&lt;int D2::*&gt;(q);  // <SPAN STYLE="font-family:Times"><I>forbidden</I></SPAN>
  }
</PRE>

<P>
<B>Proposed resolution (October, 2005):</B>
</P>

<OL>
<LI>
<P>Change 4.11&nbsp;



 <A HREF="conv.html#conv.mem">conv.mem</A> paragraph 2 as indicated:</P>
</LI>

<BLOCKQUOTE>

...If <TT>B</TT> is an inaccessible (clause 11&nbsp;



 <A HREF="access.html#class.access">class.access</A>),
ambiguous (10.2&nbsp;



 <A HREF="derived.html#class.member.lookup">class.member.lookup</A>) or virtual (10.1&nbsp;



 <A HREF="derived.html#class.mi">class.mi</A>) base class of <TT>D</TT>, <B>or a base class of a
virtual base class of <TT>D</TT>,</B> a program that necessitates this
conversion is ill-formed...

</BLOCKQUOTE>

<LI>
<P>Change 5.2.9&nbsp;



 <A HREF="expr.html#expr.static.cast">expr.static.cast</A> paragraph 2 as indicated:</P>
</LI>

<BLOCKQUOTE>

...and <TT>B</TT> is <S>not</S> <B>neither</B> a virtual base class
of <TT>D</TT> <B>nor a base class of a virtual base class
of <TT>D</TT></B>...

</BLOCKQUOTE>

<LI>
<P>Change 5.2.9&nbsp;



 <A HREF="expr.html#expr.static.cast">expr.static.cast</A> paragraph 9 as indicated:</P>
</LI>

<BLOCKQUOTE>

...and <TT>B</TT> is <S>not</S> <B>neither</B> a virtual base class
of <TT>D</TT> <B>nor a base class of a virtual base class of
<TT>D</TT></B>...

</BLOCKQUOTE>

</OL>

<BR>
<BR>
<HR>
<A NAME="506"></A>
<H4>506.
  
Conditionally-supported behavior for non-POD objects passed to ellipsis
</H4>
<B>Section: </B>5.2.2&nbsp;



 <A HREF="expr.html#expr.call">expr.call</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>DR
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>14 Apr 2005<BR>


<P>[Voted into WP at the October, 2006 meeting.]</P>

<P>The current wording of 5.2.2&nbsp;



 <A HREF="expr.html#expr.call">expr.call</A> paragraph 7
states:</P>

<BLOCKQUOTE>

When there is no parameter for a given argument, the argument is
passed in such a way that the receiving function can obtain the
value of the argument by invoking <TT>va_arg</TT>
(18.7&nbsp;



 <A HREF="lib-support.html#lib.support.runtime">lib.support.runtime</A>).  The lvalue-to-rvalue
(4.1&nbsp;



 <A HREF="conv.html#conv.lval">conv.lval</A>), array-to-pointer
(4.2&nbsp;



 <A HREF="conv.html#conv.array">conv.array</A>), and function-to-pointer
(4.3&nbsp;



 <A HREF="conv.html#conv.func">conv.func</A>) standard conversions are performed
on the argument expression.  After these conversions, if the
argument does not have arithmetic, enumeration, pointer,
pointer to member, or class type, the program is ill-formed.
If the argument has a non-POD class type (clause
9&nbsp;



 <A HREF="class.html#class">class</A>), the behavior is undefined.

</BLOCKQUOTE>

<P>Paper J16/04-0167=WG21 N1727 suggests that passing a non-POD
object to ellipsis be ill-formed.  In discussions at the
Lillehammer meeting, however, the CWG felt that the newly-approved
category of conditionally-supported behavior would be more
appropriate.</P>

<P>
<B>Proposed resolution (October, 2005):</B>
</P>

<P>Change 5.2.2&nbsp;



 <A HREF="expr.html#expr.call">expr.call</A> paragraph 7 as indicated:</P>

<BLOCKQUOTE>

...After these conversions, if the argument does not have arithmetic,
enumeration, pointer, pointer to member, or class type, the program is
ill-formed. <S>If the argument has a non-POD class type (clause 9),
the behavior is undefined.</S> <B>Passing an argument of non-POD class
type (clause 9) with no corresponding parameter is
conditionally-supported, with implementation-defined semantics.</B>

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="367"></A>
<H4>367.
  
<TT>throw</TT> operator allowed in constant expression?
</H4>
<B>Section: </B>5.19&nbsp;



 <A HREF="expr.html#expr.const">expr.const</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>DR
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Martin v. Loewis
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>29 July 2002<BR>


<P>[Voted into WP at the October, 2006 meeting.]</P>

<P>The following translation unit appears to be well-formed.</P>
<PRE>
int x[true?throw 4:5];
</PRE>
<P>According to 5.19&nbsp;



 <A HREF="expr.html#expr.const">expr.const</A>, this appears to be an
integral constant expression:
it is a conditional expression, involves only literals, and no
assignment, increment, decrement, function-call, or comma operators.
However, if this is well-formed, the standard gives no meaning to 
this declaration, since the array bound (8.3.4&nbsp;



 <A HREF="decl.html#dcl.array">dcl.array</A>
paragraph 1) cannot be computed.</P>

<P>I believe the defect is that throw expressions should also be banned
from constant expressions.</P>

<P>
<B>Notes from October 2002 meeting:</B>
</P>

<P>We should also check on <TT>new</TT> and <TT>delete</TT>.</P>

<P>
<B>Notes from the April, 2005 meeting:</B>
</P>

<P>Although it could be argued that all three of these operators
potentially involve function calls &mdash; <TT>throw</TT>
to <TT>std::terminate</TT>, <TT>new</TT> and <TT>delete</TT> to the
corresponding allocation and deallocation functions &mdash; and thus
would already be excluded from constant expressions, this reasoning
was considered to be too subtle to allow closing the issue with no
change.  A modification that explicitly clarifies the status of these
operators will be drafted.</P>

<P>
<B>Proposed resolution (October, 2005):</B>
</P>

<P>Change the last sentence of 5.19&nbsp;



 <A HREF="expr.html#expr.const">expr.const</A> as indicated:</P>

<BLOCKQUOTE>

In particular, except in <TT>sizeof</TT> expressions, functions, class
objects, pointers, or references shall not be used, and assignment,
increment, decrement, <S>function-call</S> <B>function call (including
<I>new-expression</I>s and <I>delete-expression</I>s)</B>, <S>or</S> comma
operators<B>, or <I>throw-expression</I>s</B> shall not be used.

</BLOCKQUOTE>

<P>
<I>Note: this sentence is also changed by the resolution of
<A HREF="
     cwg_active.html#530">issue 530</A>.</I>
</P>

<BR>
<BR>
<HR>
<A NAME="477"></A>
<H4>477.
  
Can <TT>virtual</TT> appear in a <TT>friend</TT> declaration?
</H4>
<B>Section: </B>7.1.2&nbsp;



 <A HREF="dcl.html#dcl.fct.spec">dcl.fct.spec</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>DR
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Daveed Vandevoorde
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>23 Sep 2004<BR>


<P>[Voted into WP at the October, 2006 meeting.]</P>

<P>I couldn't find wording that makes it invalid to say
<TT>friend&nbsp;virtual...</TT>  The closest seems to be
7.1.2&nbsp;



 <A HREF="dcl.html#dcl.fct.spec">dcl.fct.spec</A> paragraph 5, which says:</P>

<BLOCKQUOTE>

The <TT>virtual</TT> specifier shall only be used in declarations
of nonstatic class member functions that appear within a
<I>member-specification</I> of a class definition; see
10.3&nbsp;



 <A HREF="derived.html#class.virtual">class.virtual</A>.

</BLOCKQUOTE>

<P>I don't think that excludes a friend declaration (which is a
valid <I>member-specification</I> by 9.2&nbsp;



 <A HREF="class.html#class.mem">class.mem</A>).</P>

<P>
<U>John Spicer</U>: I agree that virtual should not be allowed
on friend declarations.  I think the wording in 7.1.2&nbsp;



 <A HREF="dcl.html#dcl.fct.spec">dcl.fct.spec</A> is intended to be <I>the</I> declaration of a
function within its class, although I think the wording should be
improved to make it clearer.</P>

<P>
<B>Proposed resolution (October, 2005):</B>
</P>

<P>Change 7.1.2&nbsp;



 <A HREF="dcl.html#dcl.fct.spec">dcl.fct.spec</A> paragraphs 5-6 as indicated:</P>

<BLOCKQUOTE>

<P>The <TT>virtual</TT> specifier shall <S>only</S> be
used <B>only</B> in <S>declarations</S> <B>the initial declaration</B>
of <B>a</B> non-static class member <S>functions that appear within a
<I>member-specification</I> of a class definition</S> <B>function</B>;
see <secion_ref>10.3&nbsp;



 <A HREF="derived.html#class.virtual">class.virtual</A></secion_ref>.</P>

<P>The <TT>explicit</TT> specifier shall be used only
in <S>declarations</S> <B>the declaration</B> of <S>constructors</S>
<B>a constructor</B> within <S>a</S> <B>its</B> class definition; see
12.3.1&nbsp;



 <A HREF="special.html#class.conv.ctor">class.conv.ctor</A>.</P>

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="516"></A>
<H4>516.
  
Use of <TT>signed</TT> in bit-field declarations
</H4>
<B>Section: </B>7.1.5.2&nbsp;



 <A HREF="dcl.html#dcl.type.simple">dcl.type.simple</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>DR
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>comp.std.c++
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>25 Apr 2005<BR>


<P>[Voted into WP at the October, 2006 meeting.]</P>

<P>7.1.5.2&nbsp;



 <A HREF="dcl.html#dcl.type.simple">dcl.type.simple</A> paragraph 3 reads,</P>

<BLOCKQUOTE>

It is implementation-defined whether bit-fields and objects
of <TT>char</TT> type are represented as signed or unsigned
quantities.  The <TT>signed</TT> specifier forces <TT>char</TT>
objects and bit-fields to be signed; it is redundant with other
integral types.

</BLOCKQUOTE>

<P>The last sentence in that quote is misleading w.r.t. bit-fields. The
first sentence in that quote is correct but incomplete.</P>

<P>Proposed fix: change the two sentences to read:</P>

<BLOCKQUOTE>

It is implementation-defined whether objects of <TT>char</TT> type are
represented as signed or unsigned quantities. The <TT>signed</TT>
specifier forces <TT>char</TT> objects signed; it is redundant with
other integral types except when declaring bit-fields (9.6&nbsp;



 <A HREF="class.html#class.bit">class.bit</A>).

</BLOCKQUOTE>

<P>
<B>Proposed resolution (October, 2005):</B>
</P>

<P>Change 7.1.5.2&nbsp;



 <A HREF="dcl.html#dcl.type.simple">dcl.type.simple</A> paragraph 3 as indicated:</P>

<BLOCKQUOTE>

When multiple <I>simple-type-specifier</I>s are allowed, they can be
freely intermixed with other <I>decl-specifier</I>s in any
order. <B>[<I>Note:</I></B> It is implementation-defined whether
<S>bit-fields and</S> objects of <TT>char</TT> type <B>and certain
bit-fields (9.6&nbsp;



 <A HREF="class.html#class.bit">class.bit</A>)</B> are represented as signed
or unsigned quantities.  The <TT>signed</TT> specifier
forces <B>bit-fields and</B> <TT>char</TT> objects <S>and
bit-fields</S> to be signed; it is redundant <S>with other integral
types</S> <B>in other contexts</B>. <B>&mdash;<I>end note</I>]</B>

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="540"></A>
<H4>540.
  
Propagation of cv-qualifiers in reference-to-reference collapse
</H4>
<B>Section: </B>7.3.1&nbsp;



 <A HREF="dcl.html#namespace.def">namespace.def</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>DR
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Russell Yanofsky
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>24 September 2005<BR>


<P>
<B>[Voted into the WP at the October, 2006 meeting as part of
paper J16/06-0188 = WG21 N2118.]</B>
</P>



<P>The resolution of <A HREF="
     cwg_defects.html#106">issue 106</A> specifies
that an attempt to create a type &ldquo;reference to <I>cv1</I>
<TT>T</TT>,&rdquo; where <TT>T</TT> is a typedef or template parameter
of the type &ldquo;reference to <I>cv2</I> <TT>S</TT>,&rdquo; actually
creates the type &ldquo;reference to <I>cv12</I> <TT>S</TT>,&rdquo;
where <I>cv12</I> is the union of the two sets of cv-qualifiers.</P>

<P>One objection that has been raised to this resolution is that it
is inconsistent with the treatment of cv-qualification and references
specified in 8.3.2&nbsp;



 <A HREF="decl.html#dcl.ref">dcl.ref</A> paragraph 1, which says
that cv-qualifiers applied to a typedef or template argument that is
a reference type are ignored.  For example:</P>

<PRE>
    typedef int&amp; intref;
    const intref r1;       //<SPAN STYLE="font-family:Times"><I> reference to int</I></SPAN>
    const intref&amp; r2;      //<SPAN STYLE="font-family:Times"><I> reference to const int</I></SPAN>
</PRE>

<P>In fact, however, these two declarations are quite different. In the
declaration of <TT>r1</TT>, <TT>const</TT> applies to a
&ldquo;top-level&rdquo; reference, while in the declaration of <TT>t2</TT>,
it occurs under a reference.  In general, cv-qualifiers that appear under
a reference are preserved, even if the type appears in a context in which
top-level cv-qualification is removed, for example, in determining the
type of a function from parameter types (8.3.5&nbsp;



 <A HREF="decl.html#dcl.fct">dcl.fct</A>
paragraph 3) and in template argument deduction
(14.8.2.1&nbsp;



 <A HREF="template.html#temp.deduct.call">temp.deduct.call</A> paragraph 2).</P>

<P>Another objection to the resolution is that type composition gives
different results in a single declaration than it does when separated
into two declarations.  For example:</P>

<PRE>
    template &lt;class T&gt;
    struct X {
       typedef T const T_const;
       typedef T_const&amp; type1;
       typedef T const&amp; type2;
    };

    X&lt;int&amp;&gt;::type1 t1;    // int&amp;
    X&lt;int&amp;&gt;::type2 t2;    // int const&amp;
</PRE>

<P>The initial motivation for the propagation of cv-qualification
during reference-to-reference collapse was to prevent inadvertent
loss of cv-qualifiers in contexts in which it could make a
difference.  For example, if the resolution were changed to discard,
rather than propagate, embedded cv-qualification, overload
resolution could surprisingly select a non-const version of a member
function:</P>

<PRE>
   struct X {
       void g();
       void g() const;
   };

   template &lt;typename T&gt; struct S {
       static void f(const T&amp; t) {
           t.g();    //<SPAN STYLE="font-family:Times"><I> const or non-const???</I></SPAN>
       }
   };

   X x;

   void q() {
       S&lt;X&gt;::f(x);    //<SPAN STYLE="font-family:Times"><I> calls </I></SPAN>X::g() const
       S&lt;X&amp;&gt;::f(x);   //<SPAN STYLE="font-family:Times"><I> calls </I></SPAN>X::g()
   }
</PRE>

<P>Another potentially-surprising outcome of dropping embedded
cv-qualifiers would be:</P>

<PRE>
   template &lt;typename T&gt; struct A {
       void f(T&amp;);          //<SPAN STYLE="font-family:Times"><I> mutating version</I></SPAN>
       void f(const T&amp;);    //<SPAN STYLE="font-family:Times"><I> non-mutating version</I></SPAN>
   };

   A&lt;int&amp;&gt; ai;    //<SPAN STYLE="font-family:Times"><I> Ill-formed: </I></SPAN>A&lt;int&amp;&gt;<SPAN STYLE="font-family:Times"><I> declares</I></SPAN> f(int&amp;)<SPAN STYLE="font-family:Times"><I> twice</I></SPAN>

</PRE>

<P>On the other hand, those who would like to see the resolution
changed to discard embedded cv-qualifiers observe that these examples
are too simple to be representative of real-world code.  In general,
it is unrealistic to expect that a template written with non-reference
type parameters in mind will automatically work correctly with
reference type parameters as a result of applying the issue 106
resolution.  Instead, template metaprogramming allows the template
author to choose explicitly whether cv-qualifiers are propagated or
dropped, according to the intended use of the template, and it is more
important to respect the reasonable intuition that a declaration
involving a template parameter will not change the type that the
parameter represents.</P>

<P>As a sample of real-world code, <TT>tr1::tuple</TT> was examined.
In both cases &mdash; the current resolution of issue 106 and one in
which embedded cv-qualifiers were dropped &mdash; some metaprogramming
was required to implement the intended interface, although the version
reflecting the revised resolution was somewhat simpler.</P>

<P>
<B>Notes from the October, 2005 meeting:</B>
</P>

<P>The consensus of the CWG was that the resolution of
<A HREF="
     cwg_defects.html#106">issue 106</A> should be revised not to
propagate embedded cv-qualification.</P>

<P>
<B>Note (February, 2006):</B>
</P>

<P>The wording included in the rvalue-reference paper,
J16/06-0022 = WG21 N1952, incorporates changes intended to implement
the October, 2005 consensus of the CWG.</P>

<BR>
<BR>
<HR>
<A NAME="454"></A>
<H4>454.
  
When is a definition of a static data member required?
</H4>
<B>Section: </B>9.4.2&nbsp;



 <A HREF="class.html#class.static.data">class.static.data</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>DR
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Gennaro Prota
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>18 Jan 2004<BR>


<P>[Voted into WP at the October, 2006 meeting.]</P>

<P>As a result of the resolution of <A HREF="
     cwg_defects.html#48">core issue 48</A>, the current C++ standard is not in sync with existing
practice and with user expectations as far as definitions of static
data members having const integral or const enumeration type are
concerned. Basically what current implementations do is to require a
definition only if the address of the constant is taken. Example:</P>
<PRE>
void f() {

  std::string s;
  ... 

  // current implementations don't require a definition
  if (s.find('a', 3) == std::string::npos) {
   ...
  }
</PRE>
<P>To the letter of the standard, though, the above requires a
definition of <TT>npos</TT>, since the
expression <TT>std::string::npos</TT> is potentially evaluated. I
think this problem would be easily solved with simple changes to
9.4.2&nbsp;



 <A HREF="class.html#class.static.data">class.static.data</A> paragraph 4, 9.4.2&nbsp;



 <A HREF="class.html#class.static.data">class.static.data</A> paragraph 5 and 3.2&nbsp;



 <A HREF="basic.html#basic.def.odr">basic.def.odr</A> paragraph
3.</P>


<P>Suggested resolution:</P>

<P>Replace 9.4.2&nbsp;



 <A HREF="class.html#class.static.data">class.static.data</A> paragraph 4 with:</P>
<BLOCKQUOTE>
<P>If a static data member is of const integral or const enumeration
type, its declaration in the class definition can specify a
constant-initializer which shall be [note1] an integral constant
expression (5.19). In that case, the member can appear in integral
constant expressions. No definition of the member is required, unless
an lvalue expression that designates it is potentially evaluated and
either used as operand to the built-in unary &amp; operator [note 2] or
directly bound to a reference.</P>

<P>If a definition exists, it shall be at namespace scope and shall not
contain an initializer.</P>
</BLOCKQUOTE>

<P>In 9.4.2&nbsp;



 <A HREF="class.html#class.static.data">class.static.data</A> paragraph 5 change</P>
<BLOCKQUOTE>
There shall be exactly one definition of a static data member that is
used in a program; no diagnostic is required; see 3.2.
</BLOCKQUOTE>
<P>to</P>
<BLOCKQUOTE>
Except as allowed by 9.4.2 par. 4, there shall be exactly one
definition of a static data member that is potentially evaluated (3.2)
in a program; no diagnostic is required.
</BLOCKQUOTE>

<P>In 3.2&nbsp;



 <A HREF="basic.html#basic.def.odr">basic.def.odr</A> paragraph 3 add, at the beginning:</P>
<BLOCKQUOTE>
Except for the omission allowed by 9.4.2, par. 4, ...
</BLOCKQUOTE>


<P>[note 1] Actually it shall be a "= followed by a constant-expression".
This could probably be an editorial fix, rather than a separate DR.</P>


<P>[note 2] Note that this is the case when reinterpret_cast-ing to a
reference, like in
<PRE>
struct X { static const int value = 0; };
const char &amp; c = reinterpret_cast&lt;const char&amp;&gt;(X::value);
</PRE>
 
See 5.2.10&nbsp;



 <A HREF="expr.html#expr.reinterpret.cast">expr.reinterpret.cast</A>/10</P>

<P>
<I>More information, in response to a question about why
<A HREF="
     cwg_defects.html#48">issue 48</A> does not resolve the problem:</I>
</P>

<P>The problem is that the issue was settled in a way that solves much
less than it was supposed to solve; that's why I decided to file, so
to speak, a DR on a DR.</P>

<P>I understand this may seem a little 'audacious' on my part, but please
keep reading. Quoting from the text of DR 48 (emphasis mine):</P>
<BLOCKQUOTE>
 <P>
 Originally, all static data members still had to be defined
  outside the class whether they were used or not.</P>

  <P>But that restriction was supposed to be lifted [...]</P>

  <P>In particular, if an integral/enum const static data member is
  initialized within the class, <I>and its address is never taken</I>,
  we agreed that no namespace-scope definition was required.</P>
</BLOCKQUOTE>

<P>The corresponding resolution doesn't reflect this intent, with the
definition being still required in most situations anyway: it's enough
that the constant appears outside a place where constants are
<I>required</I> (ignoring the obvious cases of sizeof and typeid) and you
have to provide a definition. For instance:</P>
<PRE>
  struct X {
   static const int c = 1;
  };

  void f(int n)
  {
   if (n == X::c)   // &lt;-- potentially evaluated
    ...
  }
</PRE>

<P>&lt;start digression&gt;</P>

<P>Most usages of non-enum BOOST_STATIC_COSTANTs, for instance, are (or
were, last time I checked) non-conforming. If you recall, Paul
Mensonides pointed out that the following template</P>
<PRE>
// map_integral

template&lt;class T, T V&gt; struct map_integral : identity&lt;T&gt; {
  static const T value = V;
};

template&lt;class T, T V&gt; const T map_integral&lt;T, V&gt;::value;
</PRE>

<P>whose main goal is to map the same couples (type, value) to the same
storage, also solves the definition problem. In this usage it is an
excellent hack (if your compiler is good enough), but IMHO still a
hack on a language defect.</P>

<P>&lt;end digression&gt;</P>

<P>What I propose is to solve the issue according to the original intent,
which is also what users expect and all compilers that I know of
already do. Or, in practice, we would have a rule that exists only as
words in a standard document.</P>

<P>PS: I've sent a copy of this to Mr. Adamczyk to clarify an important
doubt that occurred to me while writing this reply:</P>

<P>if no definition is provided for an integral static const data member
is that member an object? Paragraph 1.8/1 seems to say no, and in fact
it's difficult to think it is an object without assuming/pretending
that a region of storage exists for it (an object *is* a region of
storage according to the standard).</P>

<P>I would think that when no definition is required we have to assume
that it could be a non-object. In that case there's nothing in 3.2
which says what 'used' means for such an entity and the current
wording would thus be defective. Also, since the name of the member is
an lvalue and 3.10/2 says an lvalue refers to an object we would have
another problem.</P>

<P>OTOH the standard could pretend it is always an object (though the
compiler can optimize it away) and in this case it should probably
make a special case for it in 3.2/2.</P>

<P>
<B>Notes from the March 2004 meeting:</B>
</P>

<P>We sort of like this proposal, but we don't feel it has very
high priority.  We're not going to spend time discussing it, but
if we get drafting for wording we'll review it.</P>

<P>
<B>Proposed resolution (October, 2005):</B>
</P>

<OL>
<LI>
<P>Change the first two sentences of 3.2&nbsp;



 <A HREF="basic.html#basic.def.odr">basic.def.odr</A>
paragraph 2 from:</P>

<BLOCKQUOTE>

An expression is <I>potentially evaluated</I> unless it appears where
an integral constant expression is required (see 5.19&nbsp;



 <A HREF="expr.html#expr.const">expr.const</A>), is the operand of the <TT>sizeof</TT> operator
(5.3.3&nbsp;



 <A HREF="expr.html#expr.sizeof">expr.sizeof</A>), or is the operand of
the <TT>typeid</TT> operator and the expression does not designate an
lvalue of polymorphic class type (5.2.8&nbsp;



 <A HREF="expr.html#expr.typeid">expr.typeid</A>). An
object or non-overloaded function is <I>used</I> if its name appears
in a potentially-evaluated expression.

</BLOCKQUOTE>

<P>to</P>

<BLOCKQUOTE>

An expression that is the operand of the <TT>sizeof</TT> operator
(5.3.3&nbsp;



 <A HREF="expr.html#expr.sizeof">expr.sizeof</A>) is <I>unevaluated</I>, as is an
expression that is the operand of the <TT>typeid</TT> operator if it
is not an lvalue of a polymorphic class type (5.2.8&nbsp;



 <A HREF="expr.html#expr.typeid">expr.typeid</A>); all other expressions are <I>potentially
evaluated</I>. An object or non-overloaded function whose name appears
as a potentially-evaluated expression is <I>used</I>, unless it is an
object that satisfies the requirements for appearing in an integral
constant expression (5.19&nbsp;



 <A HREF="expr.html#expr.const">expr.const</A>) and the lvalue-to-rvalue
conversion (4.1&nbsp;



 <A HREF="conv.html#conv.lval">conv.lval</A>) is immediately applied.

</BLOCKQUOTE>

</LI>

<LI>
<P>Change the first sentence of 9.4.2&nbsp;



 <A HREF="class.html#class.static.data">class.static.data</A>
paragraph 2 as indicated:</P>
</LI>

<BLOCKQUOTE>

If a static data member is of const integral or const enumeration
type, its declaration in the class definition can specify a
<I>constant-initializer</I> <S>which</S> <B>whose <I>constant-expression</I></B>
shall be an integral constant expression (5.19&nbsp;



 <A HREF="expr.html#expr.const">expr.const</A>).

</BLOCKQUOTE>

</OL>

<BR>
<BR>
<HR>
<A NAME="58"></A>
<H4>58.
  
Signedness of bit fields of enum type
</H4>
<B>Section: </B>9.6&nbsp;



 <A HREF="class.html#class.bit">class.bit</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>DR
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Adamczyk
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>13 Oct 1998<BR>



<P>[Voted into WP at the October, 2006 meeting.]</P>

<P>Section 9.6&nbsp;



 <A HREF="class.html#class.bit">class.bit</A>

paragraph 4 needs to be more specific about the signedness of bit
fields of enum type. How much leeway does an implementation have
in choosing the signedness of a bit field? In particular, does the
phrase "large enough to hold all the values of the enumeration" mean "the
implementation decides on the signedness, and then we see whether all the
values will fit in the bit field", or does it require the implementation
to make the bit field signed or unsigned if that's what it takes to make
it "large enough"?</P>

<P>(See also <A HREF="
     cwg_defects.html#172">issue 172</A>.)</P>



<P>
<B>Note (March, 2005):</B> Clark Nelson observed that there is
variation among implementations on this point.  </P>

<P>
<B>Notes from April, 2005 meeting:</B>
</P>

<P>Although implementations enjoy a great deal of latitude in handling
bit-fields, it was deemed more user-friendly to ensure that the
example in paragraph 4 will work by requiring implementations to use
an unsigned underlying type if the enumeration type has no negative
values.  (If the implementation is allowed to choose a signed
representation for such bit-fields, the comparison against
<TT>TRUE</TT> will be <TT>false</TT>.)</P>

<P>In addition, it was observed that there is an apparent circularity
between 7.2&nbsp;



 <A HREF="dcl.html#dcl.enum">dcl.enum</A> paragraph 7 and 9.6&nbsp;



 <A HREF="class.html#class.bit">class.bit</A> paragraph 4 that should be resolved.
</P>

<P>
<B>Proposed resolution (April, 2006):</B>
</P>

<OL>

<LI>
<P>Replace 7.2&nbsp;



 <A HREF="dcl.html#dcl.enum">dcl.enum</A> paragraph 7, deleting the
embedded footnote 85, with the following:</P>

<BLOCKQUOTE>

For an enumeration where <I>e<SUB>min</SUB></I> is the smallest
enumerator and <I>e<SUB>max</SUB></I> is the largest, the values of
the enumeration are the values in the range <I>b<SUB>min</SUB></I> to
<I>b<SUB>max</SUB></I>, defined as follows: Let <I>K</I> be 1 for a
two's complement representation and 0 for a one's complement or
sign-magnitude representation.  <I>b<SUB>max</SUB></I> is the smallest
value greater than or equal to
max(|<I>e<SUB>min</SUB></I>|-<I>K</I>,|<I>e<SUB>max</SUB></I>|) and
equal to 2<I><SUP>M</SUP></I>-1, where <I>M</I> is a non-negative
integer.  <I>b<SUB>min</SUB></I> is zero if <I>e<SUB>min</SUB></I> is
non-negative and -(<I>b<SUB>max</SUB></I>+<I>K</I>) otherwise.  The
size of the smallest bit-field large enough to hold all the values of
the enumeration type is max(<I>M</I>,1) if <I>b<SUB>min</SUB></I> is
zero and <I>M</I>+1 otherwise.  It is possible to define an
enumeration that has values not defined by any of its enumerators.

</BLOCKQUOTE>
</LI>

<LI>
<P>Add the indicated text to the second sentence of
9.6&nbsp;



 <A HREF="class.html#class.bit">class.bit</A> paragraph 4:</P>

<BLOCKQUOTE>

If the value of an enumerator is stored into a bit-field of the same
enumeration type and the number of bits in the bit-field is large
enough to hold all the values of that enumeration type
<B>(7.2&nbsp;



 <A HREF="dcl.html#dcl.enum">dcl.enum</A>)</B>, the original enumerator value and
the value of the bit-field shall compare equal.

</BLOCKQUOTE>

</LI>
</OL>

<BR>
<BR>
<HR>
<A NAME="484"></A>
<H4>484.
  
Can a <I>base-specifier</I> name a cv-qualified class type?
</H4>
<B>Section: </B>10&nbsp;



 <A HREF="derived.html#class.derived">class.derived</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>DR
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Richard Corden
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>21 Oct 2004<BR>


<P>[Voted into WP at the October, 2006 meeting.]</P>

<P>
<A HREF="
     cwg_defects.html#298">Issue 298</A>, recently approved,
affirms that cv-qualified class types can be used as
<I>nested-name-specifier</I>s.  Should the same be true for
<I>base-specifier</I>s?</P>

<P>
<B>Rationale (April, 2005):</B>
</P>

<P>The resolution of <A HREF="
     cwg_defects.html#298">issue 298</A> added
new text to 9.1&nbsp;



 <A HREF="class.html#class.name">class.name</A> paragraph 5 making it
clear that a typedef that names a cv-qualified class type is a
<I>class-name</I>.  Because the definition of <I>base-specifier</I>
simply refers to <I>class-name</I>, it is already the case that
cv-qualified class types are permitted as <I>base-specifier</I>s.</P>

<P>
<B>Additional notes (June, 2005):</B>
</P>

<P>It's not completely clear what it means to have a cv-qualified
type as a <I>base-specifier</I>.  The original proposed resolution
for <A HREF="
     cwg_defects.html#298">issue 298</A> said that &ldquo;the
cv-qualifiers are ignored,&rdquo; but that wording is not in the
resolution that was ultimately approved.</P>

<P>If the cv-qualifiers are <I>not</I> ignored, does that mean that
the base-class subobject should be treated as always similarly
cv-qualified, regardless of the cv-qualification of the derived-class
lvalue used to access the base-class subobject?  For instance:</P>

<PRE>
    typedef struct B {
        void f();
        void f() const;
        int i;
    } const CB;

    struct D: CB { };

    void g(D* dp) {
        dp-&gt;f();    // which B::f?
        dp-&gt;i = 3;  // permitted?
    }
</PRE>

<P>
<B>Proposed resolution (October, 2005):</B>
</P>

<OL>
<LI>
<P>Change 9.1&nbsp;



 <A HREF="class.html#class.name">class.name</A> paragraph 5 as indicated:</P>
</LI>

<BLOCKQUOTE>

A <I>typedef-name</I> (7.1.3&nbsp;



 <A HREF="dcl.html#dcl.typedef">dcl.typedef</A>) that names a
class type, or a cv-qualified version thereof, is also
a <S><I>class-name</I>, but</S> <B><I>class-name</I>. If
a <I>typedef-name</I> that names a cv-qualified class type is used
where a <I>class-name</I> is required, the cv-qualifiers are ignored.
A <I>typedef-name</I></B> shall not be used as the <I>identifier</I>
in a
<I>class-head</I>.

</BLOCKQUOTE>

<LI>
<P>Delete 7.1.3&nbsp;



 <A HREF="dcl.html#dcl.typedef">dcl.typedef</A> paragraph 8:</P>
</LI>

<BLOCKQUOTE>

<P>[<I>Note:</I> if the <I>typedef-name</I> is used where
a <I>class-name</I> (or <I>enum-name</I>) is required, the program is
ill-formed. For example,</P>

<PRE>
    typedef struct {
        S();     //<SPAN STYLE="font-family:Times"><I> error: requires a return type because </I><TT>S</TT><I> is</I></SPAN>
                  //<SPAN STYLE="font-family:Times"><I> an ordinary member function, not a constructor</I></SPAN>
    } S;
</PRE>

<P>&mdash;<I>end note</I>]</P>

</BLOCKQUOTE>

</OL>

<BR>
<BR>
<HR>
<A NAME="494"></A>
<H4>494.
  
Problems with the resolution of issue 45
</H4>
<B>Section: </B>11&nbsp;



 <A HREF="access.html#class.access">class.access</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>DR
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Lloyd J. Lewins
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>17 Dec 2004<BR>


<P>[Voted into WP at the October, 2006 meeting.]</P>

<P>The proposed resolution for <A HREF="
     cwg_defects.html#45">issue 45</A> inserts the following sentence after 11&nbsp;



 <A HREF="access.html#class.access">class.access</A> paragraph 1:</P>

<BLOCKQUOTE>
A member of a class can also access all names as the class of
which it is a member.
</BLOCKQUOTE>

<P>I don't think that this is correctly constructed English. I see two
possibilities:</P>

<OL>
<LI>
<P>
This is a typo, and the correct change is:

<BLOCKQUOTE>
A member of a class can also access all names of the class of which
it is a member.
</BLOCKQUOTE>
</P>
</LI>

<LI>
<P>
The intent is something more like:

<BLOCKQUOTE>
A member of a nested class can also access all names accessible by
any other member of the class of which it is a member.
</BLOCKQUOTE>
</P>
</LI>
</OL>

<P>[Note: this was editorially corrected at the time defect
resolutions were being incorporated into the Working Paper to
read, &ldquo;...can also access all the names declared in the
class of which it is a member,&rdquo; which is essentially the
same as the preceding option 1.]</P>

<P>I would prefer to use the language proposed for 11.8&nbsp;



 <A HREF="access.html#class.access.nest">class.access.nest</A>:</P>

<BLOCKQUOTE>
A nested class is a member and as such has the same access rights
as any other member.
</BLOCKQUOTE>

<P>A second problem is with the text in 11.4&nbsp;



 <A HREF="access.html#class.friend">class.friend</A> paragraph 2:</P>

<BLOCKQUOTE>

[<I>Note:</I> this means that access to private and protected
names is also granted to member functions of the friend class (as
if the functions were each friends) and to the static data member
definitions of the friend class. This also means that private and
protected type names from the class granting friendship can be
used in the <I>base-clause</I> of a nested class of the friend
class. However, the declarations of members of classes nested
within the friend class cannot access the names of private and
protected members from the class granting friendship. Also,
because the <I>base-clause</I> of the friend class is not part of
its member declarations, the <I>base-clause</I> of the friend
class cannot access the names of the private and protected
members from the class granting friendship. For example,

<PRE>
    class A {
        class B { };
        friend class X;
    };
    class X : A::B {     //<SPAN STYLE="font-family:Times"><I> ill-formed: </I></SPAN>A::B<SPAN STYLE="font-family:Times"><I> cannot be accessed</I></SPAN>
                         //<SPAN STYLE="font-family:Times"><I> in the base-clause for </I></SPAN>X
        A::B mx;         //<SPAN STYLE="font-family:Times"><I> OK: </I></SPAN>A::B<SPAN STYLE="font-family:Times"><I> used to declare member of </I></SPAN>X
        class Y: A::B {  //<SPAN STYLE="font-family:Times"><I> OK: </I></SPAN>A::B<SPAN STYLE="font-family:Times"><I> used to declare member of </I></SPAN>X
            A::B my;     //<SPAN STYLE="font-family:Times"><I> ill-formed: </I></SPAN>A::B<SPAN STYLE="font-family:Times"><I> cannot be accessed</I></SPAN>
                         //<SPAN STYLE="font-family:Times"><I> to declare members of nested class of </I></SPAN>X
        };
    };
</PRE>
&mdash;<I>end note</I>]

</BLOCKQUOTE>

<P>
This seems to be an oversight. The proposed change to
11.8&nbsp;



 <A HREF="access.html#class.access.nest">class.access.nest</A> paragraph 1 would appear to have
eliminated the restrictions on nested class access.  However, at
least one compiler (gcc 3.4.3) doesn't appear to take my view,
and continues with the restrictions on access by classes within a
friend class, while implementing the rest of the resolution of
<A HREF="
     cwg_defects.html#45">issue 45</A>.
</P>

<P>
<B>Note (March, 2005):</B>
</P>



<P>
<U>Andreas Hommel</U>: I think <A HREF="
     cwg_defects.html#45">issue 45</A>
requires an additional change in 9.7&nbsp;



 <A HREF="class.html#class.nest">class.nest</A> paragraph
4:</P>

<BLOCKQUOTE>

Like a member function, a friend function (11.4&nbsp;



 <A HREF="access.html#class.friend">class.friend</A>)
defined within a nested class is in the lexical scope of that class;
it obeys the same rules for name binding as a static member function
of that class (9.4&nbsp;



 <A HREF="class.html#class.static">class.static</A>) and has no special access
rights to members of an enclosing class.

</BLOCKQUOTE>

<P>I believe the &ldquo;no special access rights&rdquo;
language should be removed.</P>

<P>
<B>Proposed resolution (October, 2005):</B>
</P>

<P>This issue is resolved by the resolution of <A HREF="
     cwg_defects.html#372">issue 372</A>.</P>

<BR>
<BR>
<HR>
<A NAME="500"></A>
<H4>500.
  
Access in <I>base-specifier</I>s of friend and nested classes
</H4>
<B>Section: </B>11.4&nbsp;



 <A HREF="access.html#class.friend">class.friend</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>DR
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Andreas Hommel
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>25 Jan 2005<BR>


<P>[Voted into WP at the October, 2006 meeting.]</P>



<P>I don't know the reason for this distinction, but it seems to be
surprising that <TT>Base::A</TT> is legal and <TT>D</TT> is illegal in
this example:
</P>

<PRE>
    class D;
    class Base 
    { 
        class A;
        class B;
        friend class D;
    }; 
    class Base::B 
    {
    };
    class Base::A : public Base::B  // OK because of issue 45
    { 
    };
    class D : public Base::B        // illegal because of 11.4p4
    { 
    };
</PRE>

<P>Shouldn't this be consistent (either way)?</P>

<P>
<B>Notes from the April, 2005 meeting:</B>
</P>

<P>In discussing <A HREF="
     cwg_defects.html#372">issue 372</A>, the CWG decided
that access in the <I>base-specifier</I>s of a class should be the
same as for its members, and that resolution will apply
to <TT>friend</TT> declarations, as well.</P>

<P>
<B>Proposed resolution (October, 2005):</B>
</P>

<P>This issue is resolved by the resolution of <A HREF="
     cwg_defects.html#372">issue 372</A>.</P>

<BR>
<BR>
<HR>
<A NAME="534"></A>
<H4>534.
  
<I>template-name</I>s and <I>operator-function-id</I>s
</H4>
<B>Section: </B>14&nbsp;



 <A HREF="template.html#temp">temp</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>DR
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Jens Maurer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>5 October 2005<BR>


<P>[Voted into WP at the October, 2006 meeting.]</P>

<P>Taken literally, 14&nbsp;



 <A HREF="template.html#temp">temp</A> paragraph 2 does not
permit operator functions to be templates:</P>

<BLOCKQUOTE>

In a function template declaration, the <I>declarator-id</I> shall be a
<I>template-name</I> (i.e., not a <I>template-id</I>).

</BLOCKQUOTE>

<P>and, in <section-ref>14.2&nbsp;



 <A HREF="template.html#temp.names">temp.names</A></section-ref> paragraph 1, a <I>template-name</I>
is defined to be simply an <I>identifier</I>.</P>

<P>
<A HREF="
     cwg_defects.html#301">Issue 301</A> considered and rejected the
idea of changing the definition of <I>template-name</I> to include
<I>operator-function-id</I>s and <I>conversion-function-id</I>s.
Either that decision should be reconsidered or the various references
in the text to <I>template-name</I> should be examined to determine
if they should also mention the non-<I>identifier</I> possibilities
for function template names.</P>

<P>
<B>Proposed resolution (April, 2006):</B>
</P>

<P>This issue is resolved by the resolution of
<A HREF="
     cwg_defects.html#301">issue 301</A>.</P>

<BR>
<BR>
<HR>
<A NAME="301"></A>
<H4>301.
  
Syntax for <I>template-name</I>
</H4>
<B>Section: </B>14.2&nbsp;



 <A HREF="template.html#temp.names">temp.names</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>DR
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mark Mitchell
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>24 Jul 2001<BR>


<P>[Voted into WP at the October, 2006 meeting.]</P>



<P>The grammar for a <I>template-name</I> is:</P>
<UL>
<I>template-name</I>:
<UL>
<I>identifier</I>
</UL>
</UL>

<P>That's not right; consider:</P>
<PRE>
    template &lt;class T&gt; T operator+(const T&amp;, const T&amp;);
    template &lt;&gt; S operator+&lt;S&gt;(const S&amp;, const S&amp;);
</PRE>

<P>This is ill-formed according to the standard, since <TT>operator+</TT> is
not a template-name.</P>

<P>
<B>Suggested resolution:</B>
</P>

<P>I think the right rule is</P>
<UL>
<I>template-name:</I>
<UL>
<I>identifier</I>
<BR>
<I>operator-function-id</I>
<BR>
<I>conversion-function-id</I>
</UL>
</UL>

<P>John Spicer adds that there's some question about whether
conversion functions should be included, as they cannot have template
argument lists.</P>

<P>
<B>Notes from 4/02 meeting:</B>
</P>

<P>If the change is made as a syntax change, we'll need a semantic
restriction to avoid <TT>operator+&lt;int&gt;</TT> as a class.
Clark Nelson will work on a compromise proposal -- not the minimal
change to the syntax proposed, not the maximal change either.</P>

<P>
<B>Clark Nelson (April 2003):</B>
</P>

<P> The proposed solution (adding <I>operator-function-id</I> as an
alternative for <I>template-name</I>) would have a large impact on
the language described by the grammar.  Specifically, for example,
<TT>operator+&lt;int&gt;</TT> would become a syntactically valid
<I>class-name</I>.  </P>

<P> On the other hand, a change with (I believe) exactly the desired
effect on the language accepted, would be to modify
<I>operator-function-id</I> itself: </P>

<UL>
<I>operator-function-id</I>:
<UL>
<TT>operator</TT> <I>operator</I>
<BR>
<B><TT>operator</TT> <I>operator</I> <TT>&lt;</TT>
<I>template-argument-list<SUB>opt</SUB></I> <TT>&gt;</TT></B>
</UL>
</UL>

<P>
<I>(Steve Adamczyk: this change was already made by
<A HREF="
     cwg_defects.html#38">issue 38</A> and is in TC1.)</I>
</P>

<P> Then there is the first sentence of 14.2&nbsp;



 <A HREF="template.html#temp.names">temp.names</A>
paragraph 3: </P>

<BLOCKQUOTE> After name lookup (3.4&nbsp;



 <A HREF="basic.html#basic.lookup">basic.lookup</A>)
finds that a name is a
<I>template-name</I>, if this name is followed by a
<TT>&lt;</TT>, the <TT>&lt;</TT> is always taken as the
beginning of a <I>template-argument-list</I> and never as a name
followed by the less-than operator.  </BLOCKQUOTE>

<P> This description seems to be adequate for names of class templates.
As far as I can tell, the only ambiguity it resolves is from something
that starts with <TT>new X &lt;</TT>, in the
scope of a class template <TT>X</TT>.  But as far as I can tell is
already inadequate for names of function templates, and is even worse
for operator function templates.  </P>

<P>Probably <TT>&lt;</TT> should always be interpreted as
introducing a <I>template-argument-list</I> if any member of the
overload set is a function template.  After all, function pointers are
very rarely compared for ordering, and it's not clear what other rule
might be workable.  </P>

<P> I'm inclined to propose the simplest rule possible for
<I>operator-function-ids</I>: if one is followed by
<TT>&lt;</TT>, then what follows is interpreted as a
<I>template-argument-list</I>, unconditionally.  Of course, if no
template for that operator has been declared, then there's an error.
</P>

<P> Also, note that if the operator in question is <TT>&lt;</TT> or <TT>&lt;&lt;</TT>, it is possible to run into a problem similar to the famous <TT>&gt;&gt;</TT> nested template argument list closing delimiter problem.
However, since in this case (at least) one of the <TT>&lt;</TT> characters has a radically different interpretation than the other, and for other reasons as well, this is unlikely to be nearly as much of a practical problem as the <TT>&gt;&gt;</TT> problem.
</P>

<P>
<B>Notes from April 2003 meeting:</B>
</P>

<P>We felt that the operator functions should not be special-cased.
They should be treated like any other name.</P>

<P>
<B>September 2003:</B>
</P>

<P>Clark Nelson has provided the changes in N1490=03-0073.</P>

<P>
<B>Notes from October 2003 meeting:</B>
</P>

<P>We reviewed Clark Nelson's N1490.  Clark will revise it and
introduce a new syntax term for an identifier or
the name of an operator function.</P>

<P>
<B>Notes from the April, 2005 meeting:</B>
</P>

<P>The CWG suggested a new approach to resolving this issue: the
existing term <I>template-id</I> will be renamed
to <I>class-template-id</I>, the term <I>template-id</I> will be
defined to include operator functions with template arguments, and any
current uses of <I>template-id</I> (such as in the definition
of <I>elaborated-type-specifier</I>) where an operator function is not
appropriate will be changed to refer to <I>class-template-id</I>.</P>

<P>
<B>Proposed resolution (April, 2006):</B>
</P>

<P>As specified in document J16/05-0156 = WG21 N1896, except that:</P>

<OL>

<LI>
<P>In change 9 (3.4.5&nbsp;



 <A HREF="basic.html#basic.lookup.classref">basic.lookup.classref</A>), omit the change from
&ldquo;entire <I>postfix-expression</I>&rdquo; to
&ldquo;<I>nested-name-specifier</I>.&rdquo;</P>
</LI>

<LI>
<P>In change a (3.4.3.1&nbsp;



 <A HREF="basic.html#class.qual">class.qual</A> paragraph 1,
third bullet), omit the change from &ldquo;entire
<I>postfix-expression</I>&rdquo; to &ldquo;<I>qualified-id</I>.&rdquo;</P>
</LI>

<LI>
<P>In change b (3.4.3.2&nbsp;



 <A HREF="basic.html#namespace.qual">namespace.qual</A> paragraph 1),
omit the change from &ldquo;entire <I>postfix-expression</I>&rdquo; to
&ldquo;<I>qualified-id</I>.&rdquo;</P>
</LI>

</OL>

<P>(Some of these omitted changes are addressed by
<A HREF="
     cwg_active.html#562">issue 562</A>.)</P>

<P>(This resolution also resolves <A HREF="
     cwg_defects.html#534">issue 534</A>.)</P>

<BR>
<BR>
<HR>
<A NAME="468"></A>
<H4>468.
  
Allow <TT>::template</TT> outside of templates
</H4>
<B>Section: </B>14.2&nbsp;



 <A HREF="template.html#temp.names">temp.names</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>DR
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>John Spicer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>9 Apr 2004<BR>


<P>[Voted into WP at the October, 2006 meeting.]</P>

<P>For the same reasons that <A HREF="
     cwg_defects.html#382">issue 382</A>
proposes for relaxation of the requirements on <TT>typename</TT>,
it would make sense to allow the <TT>::template</TT> disambiguator
outside of templates.</P>

<P>See also issues <A HREF="
     cwg_defects.html#11">11</A>,
<A HREF="
     cwg_defects.html#30">30</A>,
<A HREF="
     cwg_active.html#96">96</A>, and <A HREF="
     cwg_closed.html#109">109</A>.</P>

<P>
<B>Proposed resolution (October, 2005):</B>
</P>

<P>Change 14.2&nbsp;



 <A HREF="template.html#temp.names">temp.names</A> paragraph 5 as indicated:</P>

<BLOCKQUOTE>

If a name prefixed by the keyword <TT>template</TT> is not the name of
a template, the program is ill-formed. [<I>Note:</I> the
keyword <TT>template</TT> may not be applied to non-template members
of class templates. &mdash;<I>end note</I>] <S>Furthermore, names of
member templates shall not be prefixed by the
keyword <TT>template</TT> if the <I>postfix-expression</I>
or <I>qualified-id</I> does not appear in the scope of a template.</S>
[<I>Note:</I> just as is the case with the <TT>typename</TT> prefix,
the <TT>template</TT> prefix is allowed in cases where it is not
strictly necessary; i.e., when <B>the <I>nested-name-specifier
or</I></B> the expression on the left of the <TT>-&gt;</TT>
or <TT>.</TT><S>, or the <I>nested-name-specifier</I></S> is not
dependent on a <I>template-parameter</I><B>, or the use does not
appear in the scope of a template</B>. &mdash;<I>end note</I>]

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="372"></A>
<H4>372.
  
Is access granted by base class specifiers available in following base class specifiers?
</H4>
<B>Section: </B>14.3&nbsp;



 <A HREF="template.html#temp.arg">temp.arg</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>DR
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Clark Nelson
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>13 August 2002<BR>


<P>[Voted into WP at the October, 2006 meeting.]</P>

<P>I'm not really sure what the standard
says about this. Personally, I'd like for it to be ill-formed, but I can't
find any words that I can interpret to say so.</P>
<PRE>
  template&lt;class T&gt;
  class X
  {
  protected:
    typedef T Type;
  };
  template&lt;class T&gt;
  class Y
  {
  };
  template&lt;class T,
           template&lt;class&gt; class T1,
           template&lt;class&gt; class T2&gt;
  class Z:
    public T2&lt;typename T1&lt;T&gt;::Type&gt;,
    public T1&lt;T&gt;
  {
  };
  Z&lt;int, X, Y&gt; z;
</PRE>
<P>
<U>John Spicer</U>:
I don't think the standard really addresses this case.  There
is wording about access checking of things used as template arguments,
but that doesn't address accessing members of the template argument
type (or template) from within the template.</P>

<P>This example is similar, but does not use template template arguments.</P>
<PRE>
  class X {
  private:
    struct Type {};
  };
  template &lt;class T&gt; struct A {
    typename T::Type t;
  };
  A&lt;X&gt; ax;
</PRE>

<P>This gets an error from most compilers, though the standard is probably
mute on this as well.  An error makes sense -- if there is no error,
there is a hole in the access checking.  (The special rule about
no access checks on template parameters is not a hole, because the access
is checked on the type passed in as an argument.  But when you look
up something in the scope of a template parameter type, you need to
check the access to the member found.)</P>

<P>The logic in the template template parameter case should be similar:
anytime you look up something in a template-dependent class, the
member's access must be checked, because it could be different for
different template instances.</P>

<P>
<B>Proposed Resolution (October 2002):</B>
</P>

<P>Change the last sentence of 14.3&nbsp;



 <A HREF="template.html#temp.arg">temp.arg</A>
paragraph 3 from:
<BLOCKQUOTE>
For a <I>template-argument</I> of class type, the template definition has no
special access rights to the inaccessible members of the template
argument type.
</BLOCKQUOTE>
to:
<BLOCKQUOTE>
For a <I>template-argument</I> that is a class type or a class template, the
template definition has no special access rights to the members
of the <I>template-argument</I>.  [<I>Example</I>:
<PRE>
  template &lt;template &lt;class TT&gt; class T&gt; class A {
    typename T&lt;int&gt;::S s;
  };

  template &lt;class U&gt; class B {
    private:
    struct S { /* ... */ };
  };

  A&lt;B&gt; b;   // ill-formed, A has no access to B::S
</PRE>
-- <I>end example</I>]
</BLOCKQUOTE>
</P>

<P>
<B>Daniel Frey posts on comp.std.c++ in July 2003:</B>
I just read DR 372 and I think that the problem presented is not really 
discussed/solved properly. Consider this example:</P>
<PRE>
  class A {
  protected:
     typedef int N;
  };

  template&lt; typename T &gt;
  class B
  {};

  template&lt; typename U &gt;
  class C : public U, public B&lt; typename U::N &gt;
  {};

  C&lt; A &gt; x;
</PRE>
<P>The question is: If C is derived from A as above, is it allowed to 
access A::N before the classes opening '{'?</P>

<P>The main problem is that you need to access U's protected parts in C's 
base-clause. This pattern is common when using policies, Andrei's Loki 
library was bitten by it as he tried to make some parts of the policies 
'protected' but some compilers rejected the code. They were right to 
reject it, I think it's
11.4&nbsp;



 <A HREF="access.html#class.friend">class.friend</A>/2 that applies here and prevents the code 
above to be legal, although it addresses a different and reasonable 
example. To me, it seems wrong to reject the code as it is perfectly 
reasonable to write such stuff. The questions are:</P>

<UL>
<LI>Do you agree it's reasonable?</LI>
<LI>Is it a DR or is it a request for an extension?</LI>
<LI>Is DR 372 the right place to address it or shall it be a new DR?</LI>
</UL>

<P>
<U>Steve Adamczyk:</U>
In other words, the point of the issue is over what range access derived
from base class specifiers is granted, and whether any part of that range 
is the base specifier list itself, either the parts afterwards or the whole 
base specifier list.  (Clark Nelson confirms this is what he was
asking with the original question.)
Personally, I find it somewhat disturbing that access might
arrive incrementally; I'd prefer that the access happen all 
at once, at the opening brace of the class.</P>

<P>
<B>Notes from October 2003 meeting:</B>
</P>

<P>We decided it makes sense to delay the access checking for the
base class specifiers until the opening brace of the class is
seen.  In other words, the base specifiers will be checked using
the full access available for the class, and the order of the
base classes is not significant in that determination. The
implementors present all said they already had code to handle
accumulation of delayed access checks, because it is already
needed in other contexts.</P>

<P>
<B>Proposed resolution (October, 2004):</B>
</P>

<OL>

<LI>
<P>Change the last sentence of 14.3&nbsp;



 <A HREF="template.html#temp.arg">temp.arg</A>
paragraph 3 as indicated:</P>

<BLOCKQUOTE>

For a <I>template-argument</I> <S>of</S> <B>that is a</B> class
type <B>or a class template</B>, the template definition
has no special access rights to the <S>inaccessible</S> members of the
<S>template argument type</S> <B><I>template-argument</I>.
[<I>Example:</I>

<PRE>
    template &lt;template &lt;class TT&gt; class T&gt; class A {
       typename T&lt;int&gt;::S s;
    };

    template &lt;class U&gt; class B {
       private:
       struct S { /* ... */ };
    };

    A&lt;B&gt; b;   // ill-formed, A has no access to B::S
</PRE>

<P>&mdash;<I>end example</I>]</P>

</B>

</BLOCKQUOTE>

</LI>

<LI>
<P>Insert the following as a new paragraph after the final
paragraph of 11&nbsp;



 <A HREF="access.html#class.access">class.access</A>:</P>

<BLOCKQUOTE>

<P>The access of names in a class <I>base-specifier-list</I> are
checked at the end of the list after all base classes are known.
[<I>Example:</I>
</P>

<PRE>
    class A {
      protected:
         typedef int N;
    };

    template&lt;typename T&gt; class B {};

    template&lt;typename U&gt; class C : public B&lt;typename U::N&gt;, public U {};

    C&lt;A&gt; x;  // OK: A is a base class so A::N in B&lt;A::N&gt; is accessible
</PRE>

</BLOCKQUOTE>

<P>&mdash;<I>end example</I>]</P>

</LI>

</OL>

<P>
<B>Notes from the April, 2005 meeting:</B>
</P>

<P>The 10/2004 resolution is not sufficient to implement the CWG's
intent to allow these examples: clause 11&nbsp;



 <A HREF="access.html#class.access">class.access</A>
paragraph 1 grants protected access only to &ldquo;members and
friends&rdquo; of derived classes, not to their
<I>base-specifier</I>s.  The resolution needs to be extended to say
either that access in <I>base-specifiers</I> is determined as if they
were members of the class being defined or that access is granted to
the class as an entity, including its <I>base-specifier</I>s.  See
also <A HREF="
     cwg_defects.html#500">issue 500</A>, which touches on the same
issue and should be resolved in the same way.</P>

<P>
<B>Proposed resolution (October, 2005):</B>
</P>

<OL>

<LI>
<P>Change the second bullet of 11&nbsp;



 <A HREF="access.html#class.access">class.access</A> paragraph
1 as indicated:</P>

<UL>
<LI>
<P>
<TT>protected</TT>; that is, its name can be used only by
members and friends of the class in which it is declared, <S>and by
members and friends of classes derived from this class</S> <B>by
classes derived from that class, and by their friends</B> (see
11.5&nbsp;



 <A HREF="access.html#class.protected">class.protected</A>).</P>
</LI>
</UL>

</LI>

<LI>
<P>Change 11&nbsp;



 <A HREF="access.html#class.access">class.access</A> paragraph 2 as indicated:</P>

<BLOCKQUOTE>

A member of a class can also access all the names <S>declared in the
class of which it is a member</S> <B>to which the class has access</B>.

</BLOCKQUOTE>

</LI>

<LI>
<P>Change 11&nbsp;



 <A HREF="access.html#class.access">class.access</A> paragraph 6 as indicated:</P>

<BLOCKQUOTE>

All access controls in clause 11&nbsp;



 <A HREF="access.html#class.access">class.access</A> affect the
ability to access a class member name from a particular scope. <S>The
access control for names used in the definition of a class member that
appears outside of the member's class definition is done as if the
entire member definition appeared in the scope of the member's
class.</S> <B>For purposes of access control, the <I>base-specifier</I>s
of a class and the definitions of class members that appear outside of
the class definition are considered to be within the scope of that
class.</B> In particular...

</BLOCKQUOTE>

</LI>

<LI>
<P>Change the example and commentary in 11&nbsp;



 <A HREF="access.html#class.access">class.access</A>
paragraphs 6-7 as indicated:</P>

<BLOCKQUOTE>

<P>[<I>Example:</I>
</P>

<PRE>
    class A {
      typedef int I; //<SPAN STYLE="font-family:Times"><I> private member</I></SPAN>
      I f();
      friend I g(I);
      static I x;
    <B>protected:
      struct B { };</B>
    };

    A::I A::f () { return 0; }
    A::I g(A::I p = A::x);
    A::I g(A::I p) { return 0; }
    A::I A::x = 0;

    <B>struct D: A::B, A { };</B>
</PRE>

Here, all the uses of <TT>A::I</TT> are well-formed
because <TT>A::f</TT> and <TT>A::x</TT> are members of
class <TT>A</TT> and <TT>g</TT> is a friend of class <TT>A</TT>.  This
implies, for example, that access checking on the first use
of <TT>A::I</TT> must be deferred until it is determined that this use
of <TT>A::I</TT> is as the return type of a member of
class <TT>A</TT>. <B>Similarly, the use of <TT>A::B</TT> as a
<I>base-specifier</I> is well-formed because <TT>D</TT> is derived
from <TT>A</TT>, so access checking of <I>base-specifier</I>s must be
deferred until the entire <I>base-specifier-list</I> has been seen.</B>
&mdash;<I>end example</I>]

</BLOCKQUOTE>

</LI>

<LI>
<P>In 11.4&nbsp;



 <A HREF="access.html#class.friend">class.friend</A> paragraph 2, replace the following
text:</P>

<BLOCKQUOTE>

<P>Declaring a class to be a friend implies that the names of private
and protected members from the class granting friendship can be
accessed in declarations of members of the befriended
class. [<I>Note:</I> this means that access to private and protected
names is also granted to member functions of the friend class (as if
the functions were each friends) and to the static data member
definitions of the friend class. This also means that private and
protected type names from the class granting friendship can be used in
the <I>base-clause</I> of a nested class of the friend class. However,
the declarations of members of classes nested within the friend class
cannot access the names of private and protected members from the
class granting friendship. Also, because the <I>base-clause</I> of the
friend class is not part of its member declarations,
the <I>base-clause</I> of the friend class cannot access the names of
the private and protected members from the class granting
friendship. For example,</P>

<PRE>
    class A {
      class B { };
      friend class X;
    };
    class X: A::B {     //<SPAN STYLE="font-family:Times"><I> ill-formed: </I><TT>A::B</TT><I> cannot be accessed</I></SPAN>
                        //<SPAN STYLE="font-family:Times"><I> in the base-clause for </I><TT>X</TT></SPAN>
      A::B mx;          //<SPAN STYLE="font-family:Times"><I> OK: </I><TT>A::B</TT><I> used to declare member of </I><TT>X</TT></SPAN>
      class Y: A::B {   //<SPAN STYLE="font-family:Times"><I> OK: </I><TT>A::B</TT><I> used to declare member of </I><TT>X</TT></SPAN>
        A::B my;        //<SPAN STYLE="font-family:Times"><I> ill-formed: </I><TT>A::B</TT><I> cannot be accessed</I></SPAN>
                        //<SPAN STYLE="font-family:Times"><I> to declare members of nested class of </I><TT>X</TT></SPAN>
      };
    };
</PRE>

<P>&mdash;<I>end note</I>]</P>

</BLOCKQUOTE>

<P>with:</P>

<BLOCKQUOTE>

<P>Declaring a class to be a friend implies that the names of private and
protected members from the class granting friendship can be accessed
in the <I>base-specifier</I>s and member declarations of the befriended
class. [<I>Example:</I>
</P>

<PRE>
    class A {
      class B { };
      friend class X;
    };

    struct X: A::B {   //<SPAN STYLE="font-family:Times"><I> OK: </I><TT>A::B</TT><I> accessible to friend</I></SPAN>
      A::B mx;         //<SPAN STYLE="font-family:Times"><I> OK: </I><TT>A::B</TT><I> accessible to member of friend</I></SPAN>
      class Y {
        A::B my;       //<SPAN STYLE="font-family:Times"><I> OK: </I><TT>A::B</TT><I> accessible to nested member of friend</I></SPAN>
      };
    };
</PRE>

<P>&mdash;<I>end example</I>]</P>

</BLOCKQUOTE>

</LI>

<LI>
<P>Change the last sentence of 14.3&nbsp;



 <A HREF="template.html#temp.arg">temp.arg</A> paragraph 3
as indicated:</P>

<BLOCKQUOTE>

<P>For a <I>template-argument</I> <S>of</S> <B>that is a</B> class type
<B>or a class template</B>, the template definition has no special
access rights to the <S>inaccessible</S> members of the <S>template
argument type.</S> <B><I>template-argument</I>.  [<I>Example:</I></B>
</P>

<PRE>
<B>
    template &lt;template &lt;class TT&gt; class T&gt; class A {
      typename T&lt;int&gt;::S s;
    };

    template &lt;class U&gt; class B {
    private:
      struct S { /* ... */ };
    };

    A&lt;B&gt; b;    //<SPAN STYLE="font-family:Times"><I> ill-formed, </I><TT>A</TT><I> has no access to </I><TT>B::S</TT></SPAN>
</B>
</PRE>

<P>
<B>&mdash;<I>end example</I>]</B>
</P>

</BLOCKQUOTE>

</LI>

<LI>
<P>Change 9.7&nbsp;



 <A HREF="class.html#class.nest">class.nest</A> paragraph 4 as indicated:</P>

<BLOCKQUOTE>

Like a member function, a friend function (11.4&nbsp;



 <A HREF="access.html#class.friend">class.friend</A>)
defined within a nested class is in the lexical scope of that class;
it obeys the same rules for name binding as a static member function
of that class (9.4&nbsp;



 <A HREF="class.html#class.static">class.static</A>)<B>, but it</B> <S>and</S>
has no special access rights to members of an enclosing class.

</BLOCKQUOTE>

</LI>

</OL>

<P>
<I>(Note: this resolution also resolves issues <A HREF="
     cwg_defects.html#494">494</A> and <A HREF="
     cwg_defects.html#500">500</A>.)</I>
</P>

<BR>
<BR>
<HR>
<A NAME="517"></A>
<H4>517.
  
Partial specialization following explicit instantiation
</H4>
<B>Section: </B>14.5.4&nbsp;



 <A HREF="template.html#temp.class.spec">temp.class.spec</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>DR
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>John Spicer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>03 May 2005<BR>


<P>[Voted into WP at the October, 2006 meeting.]</P>

<P>According to 14.5.4&nbsp;



 <A HREF="template.html#temp.class.spec">temp.class.spec</A> paragraph 1,</P>

<BLOCKQUOTE>

If a template is partially specialized then that partial
specialization shall be declared before the first use of that partial
specialization that would cause an implicit instantiation to take
place, in every translation unit in which such a use occurs; no
diagnostic is required.

</BLOCKQUOTE>

<P>This leaves the impression that an explicit instantiation of the
primary template may precede the declaration of an applicable partial
specialization.  Is the following example well-formed?</P>

<PRE>
    template&lt;typename T&gt; class X{
        public:
        void foo(){};
    };

    template class X&lt;void *&gt;;

    template&lt;typename T&gt; class X&lt;T*&gt;{
        public:
        void baz();
    };

    void bar() {
        X&lt;void *&gt; x;
        x.foo();
    }
</PRE>

<P>
<B>Proposed resolution (October, 2005):</B>
</P>

<P>Replace the last sentence of 14.5.4&nbsp;



 <A HREF="template.html#temp.class.spec">temp.class.spec</A>
paragraph 1:</P>

<BLOCKQUOTE>

If a template is partially specialized then that partial
specialization shall be declared before the first use of that partial
specialization that would cause an implicit instantiation to take
place, in every translation unit in which such a use occurs; no
diagnostic is required.

</BLOCKQUOTE>

<P>with:</P>

<BLOCKQUOTE>

A partial specialization shall be declared before the first use of a
class template specialization that would make use of the partial
specialization as the result of an implicit or explicit instantiation
in every translation unit in which such a use occurs; no diagnostic is
required.

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="515"></A>
<H4>515.
  
Non-dependent references to base class members
</H4>
<B>Section: </B>14.6.2&nbsp;



 <A HREF="template.html#temp.dep">temp.dep</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>DR
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>18 Apr 2005<BR>


<P>[Voted into WP at the October, 2006 meeting.]</P>

<P>Implementations vary in their treatment of the following code:</P>

<PRE>
    struct A {
      int foo_;
    };
    template &lt;typename T&gt; struct B: public A { };
    template &lt;typename T&gt; struct C: B&lt;T&gt; {
      int foo() {
        return A::foo_;  //<SPAN STYLE="font-family:Times"><I> #1</I></SPAN>
      }
    };
    int f(C&lt;int&gt;* p) {
      return p-&gt;foo();
    }
</PRE>

<P>According to <A HREF="http://gcc.gnu.org/bugzilla/show_bug.cgi?id=21008">one
analysis</A>, because the expression <TT>A::foo_</TT> on line #1
is non-dependent, it must be analyzed in the definition
context.  It that context, it violates the restrictions of
9.2&nbsp;



 <A HREF="class.html#class.mem">class.mem</A> paragraph 10 on how the name of a
nonstatic data member of a class can be used and thus should be
treated as an error.</P>

<P>On the other hand, the description of the transformation of
an <I>id-expression</I> into a class member access expression
(9.3.1&nbsp;



 <A HREF="class.html#class.mfct.nonstatic">class.mfct.nonstatic</A> paragraph 3) does not have any special
treatment of templates; when <TT>C&lt;int&gt;::foo()</TT> is
instantiated, the reference to <TT>A::foo_</TT> turns out to be to a
base class member and is thus transformed into
<TT>(*this).A::foo_</TT> and is thus not an error.</P>

<P>
<B>Proposed resolution (October, 2005):</B>
</P>

<P>Change 9.3.1&nbsp;



 <A HREF="class.html#class.mfct.nonstatic">class.mfct.nonstatic</A> paragraph 3 as indicated:</P>

<BLOCKQUOTE>

When an <I>id-expression</I> (5.1&nbsp;



 <A HREF="expr.html#expr.prim">expr.prim</A>) that is not
part of a class member access syntax (5.2.5&nbsp;



 <A HREF="expr.html#expr.ref">expr.ref</A>)
and not used to form a pointer to member (5.3.1&nbsp;



 <A HREF="expr.html#expr.unary.op">expr.unary.op</A>) is used in the body of a non-static member function
of class <TT>X</TT> or used in the <I>mem-initializer</I> for a
constructor of class <TT>X</TT>, if name lookup (3.4.1&nbsp;



 <A HREF="basic.html#basic.lookup.unqual">basic.lookup.unqual</A>) resolves the name in the <I>id-expression</I> to a
non-static non-type member of <S>class <TT>X</TT> or of a base class
of <TT>X</TT></S> <B>some class <TT>C</TT></B>,
the <I>id-expression</I> is transformed into a class member access
expression (5.2.5&nbsp;



 <A HREF="expr.html#expr.ref">expr.ref</A>) using <TT>(*this)</TT>
(9.3.2&nbsp;



 <A HREF="class.html#class.this">class.this</A>) as the
<I>postfix-expression</I> to the left of the <TT>.</TT>
operator.  <B>[<I>Note:</I> If <TT>C</TT> is not <TT>X</TT> or a base
class of <TT>X</TT>, the class member access expression is ill-formed.
&mdash;<I>end note</I>]</B> <S>The member name then refers to the
member of the object for which the function is called.</S> Similarly
during name lookup...

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="524"></A>
<H4>524.
  
Can function-notation calls to operator functions be dependent?
</H4>
<B>Section: </B>14.6.2&nbsp;



 <A HREF="template.html#temp.dep">temp.dep</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>DR
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Daveed Vandevoorde
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>19 July 2005<BR>


<P>[Voted into WP at the October, 2006 meeting.]</P>

<P>The description of dependent function calls in
14.6.2&nbsp;



 <A HREF="template.html#temp.dep">temp.dep</A> paragraph 1 applies only to
<I>identifier</I>s in postfix-notation function calls and to operator
notation calls for operator functions:</P>

<BLOCKQUOTE>

<P>In an expression of the form:</P>

<UL>
<I>postfix-expression</I> <TT>(</TT> <I>expression-list<SUB>opt</SUB></I> <TT>)</TT>
</UL>

<P>where the <I>postfix-expression</I> is an <I>identifier</I>,
the <I>identifier</I> denotes a <I>dependent name</I> if and only if
any of the expressions in the <I>expression-list</I> is a
type-dependent expression (14.6.2.2&nbsp;



 <A HREF="template.html#temp.dep.expr">temp.dep.expr</A>). If an
operand of an operator is a type-dependent expression, the operator
also denotes a dependent name.</P>

</BLOCKQUOTE>

<P>It would appear from the related passage in
14.6.4.2&nbsp;



 <A HREF="template.html#temp.dep.candidate">temp.dep.candidate</A> paragraph 1 that the description of
postfix-notation function calls should apply to all
<I>unqualified-id</I>s that are not <I>template-id</I>s,
including <I>operator-function-id</I>s, not just to
<I>identifier</I>s:</P>

<BLOCKQUOTE>

For a function call that depends on a template parameter, if the
function name is an <I>unqualified-id</I> but not
a <I>template-id</I>, the candidate functions are found...

</BLOCKQUOTE>

<P>
<B>Proposed resolution (October, 2005):</B>
</P>

<OL>
<LI>
<P>Change 14.6.2&nbsp;



 <A HREF="template.html#temp.dep">temp.dep</A> paragraph 1 as
indicated:</P>
</LI>

<BLOCKQUOTE>

<P>...In an expression of the form:</P>

<UL>
<I>postfix-expression </I><TT>(</TT><I> expression-list<SUB>opt</SUB> </I><TT>)</TT>
</UL>

<P>where the <I>postfix-expression</I> is an <S><I>identifier</I></S>
<B><I>unqualified-id</I> but not a <I>template-id</I></B>,
the <S><I>identifier</I></S> <B><I>unqualified-id</I></B> denotes
a <I>dependent name</I> if and only if any of the expressions in
the <I>expression-list</I> is a type-dependent expression
(14.6.2.2&nbsp;



 <A HREF="template.html#temp.dep.expr">temp.dep.expr</A>)...</P>

</BLOCKQUOTE>

<LI>
<P>Change 14.6.4.2&nbsp;



 <A HREF="template.html#temp.dep.candidate">temp.dep.candidate</A> paragraph 1 as
indicated:</P>
</LI>

<BLOCKQUOTE>

For a function call that depends on a template parameter, if the
function name is an <I>unqualified-id</I> but not
a <I>template-id</I>, <B>or if the function is called using operator
notation,</B> the candidate functions are found using the
usual lookup rules (3.4.1&nbsp;



 <A HREF="basic.html#basic.lookup.unqual">basic.lookup.unqual</A>, 3.4.2&nbsp;



 <A HREF="basic.html#basic.lookup.argdep">basic.lookup.argdep</A>) except that...

</BLOCKQUOTE>

</OL>

<P>(See also <A HREF="
     cwg_active.html#561">issue 561</A>.)</P>

<BR>
<BR>
<HR>
<A NAME="522"></A>
<H4>522.
  
Array-to-pointer decay in template argument deduction
</H4>
<B>Section: </B>14.8.2.1&nbsp;



 <A HREF="template.html#temp.deduct.call">temp.deduct.call</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>DR
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Daveed Vandevoorde
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>3 June 2005<BR>


<P>[Voted into WP at the October, 2006 meeting.]</P>

<P>Consider the following example:</P>

<PRE>
    char* cmdline3_[1] = {};

    template&lt;class charT&gt;
    void func(const charT* const argv[]) {}

    int main()
    {
        func(cmdline3_);
    }
</PRE>

<P>In terms of the process described in 14.8.2.1&nbsp;



 <A HREF="template.html#temp.deduct.call">temp.deduct.call</A>,
<TT>P</TT> is <TT>const charT* const *</TT> and <TT>A</TT> is
<TT>char*[1]</TT>.  According to the first bullet in paragraph 2,
the type used in deduction is not <TT>A</TT> but &ldquo;the pointer
type produced by the array-to-pointer standard conversion.&rdquo;</P>

<P>According to paragraph 4,</P>

<BLOCKQUOTE>

In general, the deduction process attempts to find template argument
values that will make the deduced <TT>A</TT> identical to <TT>A</TT>
(after the type <TT>A</TT> is transformed as described
above). However, there are three cases that allow a difference:

</BLOCKQUOTE>

<P>In this example, the deduced <TT>A</TT> is <I>not</I>
identical to the transformed <TT>A</TT>, because the deduced
<TT>A</TT> has additional cv-qualification, so the three exceptions
must be examined to see if they apply.  The only one that might
apply is the second bullet of paragraph 4:</P>

<BLOCKQUOTE>

<UL>
<LI>
<TT>A</TT> can be another pointer or pointer to member type
that can be converted to the deduced <TT>A</TT> via a qualification
conversion (4.4&nbsp;



 <A HREF="conv.html#conv.qual">conv.qual</A>).</LI>
</UL>

</BLOCKQUOTE>

<P>However, <TT>A</TT> is not a pointer type but an array type;
this provision does not apply and deduction fails.</P>

<P>It has been argued that the phrase &ldquo;after the type <TT>A</TT>
is transformed as described above&rdquo; should be understood to
apply to the <TT>A</TT> in the three bullets of paragraph 4.  If
that is the intent, the wording should be changed to make that
explicit.</P>

<P>
<B>Proposed resolution (October, 2005):</B>
</P>

<P>Add the indicated words to 14.8.2.1&nbsp;



 <A HREF="template.html#temp.deduct.call">temp.deduct.call</A>
paragraph 4:</P>

<BLOCKQUOTE>

<P>In general, the deduction process attempts to find template
argument values that will make the deduced <TT>A</TT> identical
to <TT>A</TT> (after the type <TT>A</TT> is transformed as described
above). However, there are three cases that allow a difference:</P>

<UL>

<LI>
<P>If the original <TT>P</TT> is a reference type, the
deduced <TT>A</TT> (i.e., the type referred to by the reference) can
be more cv-qualified than <B>the transformed</B> <TT>A</TT>.</P>
</LI>

<LI>
<P>
<B>The transformed</B> <TT>A</TT> can be another pointer or
pointer to member type that can be converted to the deduced <TT>A</TT>
via a qualification conversion (4.4&nbsp;



 <A HREF="conv.html#conv.qual">conv.qual</A>).</P>
</LI>

<LI>
<P>If <TT>P</TT> is a class, and <TT>P</TT> has the
form <I>template-id</I>, then <B>the transformed</B> <TT>A</TT> can be
a derived class of the deduced <TT>A</TT>. Likewise, if <TT>P</TT> is
a pointer to a class of the form <I>template-id</I>, <B>the
transformed</B> <TT>A</TT> can be a pointer to a derived class pointed
to by the deduced <TT>A</TT>.</P>
</LI>

</UL>

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="526"></A>
<H4>526.
  
Confusing aspects in the specification of non-deduced contexts
</H4>
<B>Section: </B>14.8.2.5&nbsp;



 <A HREF="template.html#temp.deduct.type">temp.deduct.type</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>DR
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>25 July 2005<BR>


<P>[Voted into WP at the October, 2006 meeting.]</P>

<P>14.8.2.5&nbsp;



 <A HREF="template.html#temp.deduct.type">temp.deduct.type</A> paragraph 5 reads:</P>

<BLOCKQUOTE>

<P>The non-deduced contexts are:</P>

<UL>

<LI>
<P>The <I>nested-name-specifier</I> of a type that was specified
using a <I>qualified-id</I>.</P>
</LI>

<LI>
<P>A non-type template argument or an array bound that is an
expression that references a template parameter.</P>
</LI>

<LI>
<P>A template parameter used in the parameter type of a function
parameter that has a default argument that is being used in the call
for which argument deduction is being done.</P>
</LI>

<LI>
<P>A function parameter for which argument deduction cannot be
done because the associated function argument is a function, or a set
of overloaded functions (13.4&nbsp;



 <A HREF="over.html#over.over">over.over</A>), and one or more
of the following apply:</P>
</LI>

<UL>

<LI>
<P>more than one function matches the function parameter type
(resulting in an ambiguous deduction), or</P>
</LI>

<LI>
<P>no function matches the function parameter type, or</P>
</LI>

<LI>
<P>the set of functions supplied as an argument contains one or
more function templates.</P>
</LI>

</UL>

<LI>
<P>An array bound that is an expression that references
a <I>template-parameter</I>.</P>
</LI>

</UL>

</BLOCKQUOTE>

<P>There are two problems with this list:</P>

<OL>

<LI>
<P>The last bullet is redundant with the second bullet.  This
appears to have been the result of applying the resolutions of issues
<A HREF="
     cwg_defects.html#70">70</A> and <A HREF="
     cwg_defects.html#352">352</A>
independently instead of in coordination.</P>
</LI>

<LI>
<P>The second bullet
appears to be contradicted by the statement in paragraph 8 saying that
an argument can be deduced if <TT>P</TT> and <TT>A</TT> have the
forms <I>type</I><TT>[i]</TT> and
<I>template-name</I><TT>&lt;i&gt;</TT>.</P>

<P>The intent of the wording in bullet 2 appears to have been that
deduction cannot be done if the template parameter is a sub-expression
of the template argument or array bound expression and that it can be
done if it is the complete expression, but the current wording does
not say that very clearly.  (Similar wording also appears in
14.6.2.1&nbsp;



 <A HREF="template.html#temp.dep.type">temp.dep.type</A> paragraph 3 and 14.8.2.5&nbsp;



 <A HREF="template.html#temp.deduct.type">temp.deduct.type</A> paragraph 14.)</P>
</LI>

</OL>

<P>
<B>Proposed resolution (October, 2005):</B>
</P>

<OL>
<LI>
<P>Change 14.8.2.5&nbsp;



 <A HREF="template.html#temp.deduct.type">temp.deduct.type</A> paragraph 5 as
indicated:</P>
</LI>

<BLOCKQUOTE>

<P>The non-deduced contexts are:</P>

<UL>
<LI>
<P>The <I>nested-name-specifier</I> of a type that was specified
using a <I>qualified-id</I>.</P>
</LI>

<LI>
<P>A non-type template argument or an array bound <S>that is an
expression that</S> <B>in either of which a subexpression</B>
references a template parameter.</P>
</LI>

<LI>
<P>A template parameter used in the parameter type of a function
parameter that has a default argument that is being used in the call
for which argument deduction is being done.</P>
</LI>

<LI>
<P>A function parameter for which argument deduction cannot be done
because the associated function argument is a function, or a set of
overloaded functions (13.4&nbsp;



 <A HREF="over.html#over.over">over.over</A>), and one or more of
the following apply:</P>
</LI>

<UL>
<LI>
<P>more than one function matches the function parameter type
(resulting in an ambiguous deduction), or</P>
</LI>

<LI>
<P>no function matches the function parameter type, or</P>
</LI>

<LI>
<P>the set of functions supplied as an argument contains one or more function templates.</P>
</LI>
</UL>

<S>
<LI>
<P>An array bound that is an expression that references a
<I>template-parameter</I>.</P>
</LI>
</S>
</UL>

</BLOCKQUOTE>

<LI>
<P>Change 14.8.2.5&nbsp;



 <A HREF="template.html#temp.deduct.type">temp.deduct.type</A> paragraph 14 as
indicated:</P>
</LI>

<BLOCKQUOTE>

If, in the declaration of a function template with a non-type template
parameter, the non-type template parameter is used in <S>an
expression</S> <B>a subexpression</B> in the function parameter list,
the expression is a non-deduced context <B>as specified above</B>...

</BLOCKQUOTE>

<LI>
<P>Change 14.6.2.1&nbsp;



 <A HREF="template.html#temp.dep.type">temp.dep.type</A> paragraph 3 as
indicated:</P>
</LI>

<BLOCKQUOTE>

A template argument that is equivalent to a template parameter (i.e.,
has the same constant value or the same type as the template
parameter) can be used in place of that template parameter in a
reference to the current instantiation. In the case of a non-type
template argument, the argument must have been given the value of the
template parameter and not an expression <S>involving</S> <B>that
contains</B> the template parameter <B>as a subexpression</B>...

</BLOCKQUOTE>

</OL>

<BR>
<BR>
<HR>
<A NAME="415"></A>
<H4>415.
  
Template deduction does not cause instantiation
</H4>
<B>Section: </B>14.8.3&nbsp;



 <A HREF="template.html#temp.over">temp.over</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>DR
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>John Spicer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>4 May 2003<BR>


<P>[Voted into WP at the October, 2006 meeting.]</P>



<P>
<U>Mike Miller:</U>
In fact, now that I've looked more closely, that appears not to be the
case.  (At least, it's not the error I get when I compile his example.)
Here's a minimal extract (without the inflammatory using-directive :-)
that illustrates what I think is going on:</P>
<PRE>
  template &lt;typename _Iterator&gt;
  struct iterator_traits {
    typedef typename _Iterator::difference_type difference_type;
  };

  template &lt;typename _InputIterator&gt;
  inline typename iterator_traits&lt;_InputIterator&gt;::difference_type
  distance(_InputIterator, _InputIterator);

  double distance(const int&amp;, const int&amp;);

  void f() {
    int i = 0;
    int j = 0;
    double d = distance(i, j);
  }
</PRE>
<P>What happens is that <TT>iterator_traits&lt;int&gt;</TT>
is instantiated as part of
type deduction for the function template <TT>distance</TT>,
 and the instantiation
fails.  (Note that it can't be instantiation of <TT>distance&lt;int&gt;</TT>,
as I had originally posited, because in this case only a declaration, not a
definition, of that template is in scope.)</P>

<P>
<U>John Spicer:</U> Yes, I believe that is what is going on.</P>

<P>
<U>Mike Miller:</U> 
I seem to recall that there was some discussion of questions related
to this during the core meetings in Oxford.  I think Steve Adamczyk
said something to the effect that it's infeasible to suppress all
instantiation errors during template type deduction and simply call
any such errors a deduction failure.  (I could be misremembering, and
I could be misapplying that comment to this situation.)</P>

<P>
<U>John Spicer</U>:
Regardless of other conditions in which this may apply, I don't think
it would be reasonable for compilers to have to do "speculative
instantiations" during template argument deduction.  One class
instantiation could kick off a series of other instantiations, etc.</P>

<P>
<U>Mike Miller:</U>
I don't see anything in the Standard that tells me whether it's
legitimate or not to report an error in this case.  I hope John or
another template expert can enlighten me on that.</P>

<P>
<U>John Spicer:</U>
My opinion is that, because this case is not among those enumerated
that cause deduction failure (rather than being ill-formed) that
reporting an error is the right thing to do.</P>

<P>
<U>Mike Miller:</U>
I am still interested, though, in the question of why
14.8.3&nbsp;



 <A HREF="template.html#temp.over">temp.over</A> says that
viable function template specializations are instantiated, even if they
are not selected by overload resolution.</P>

<P>
<U>John Spicer:</U>
I believe the wording in
14.8.3&nbsp;



 <A HREF="template.html#temp.over">temp.over</A> is incorrect.  I researched this and
found that a change was made during the clause 14 restructuring that
was incorporated in March of 1996.  The prior wording was "the deduced
template arguments are used to generate a single template function".
This was changed to "deduced template arguments are used to
instantiate a single function template specialization".  I believe
this resulted from what was basically a global replace of "generate"
with "instantiate" and of "template function" with "function template
specialization".  In this case, the substitution changed the meaning.
This paragraph needs reworking.</P>

<P>
<B>Proposed resolution (April, 2006):</B>
</P>

<P>Change 14.8.3&nbsp;



 <A HREF="template.html#temp.over">temp.over</A> paragraph 1 as indicated:</P>

<BLOCKQUOTE>

...For each function template, if the argument deduction and checking
succeeds, the <I>template-argument</I>s (deduced and/or explicit) are used to
<S>instantiate</S> <B>synthesize the declaration of</B> a single
function template specialization which is added to the candidate
functions set to be used in overload resolution. If, for a given
function template, argument deduction fails, no such function is added
to the set of candidate functions for that template. The complete set
of candidate functions includes all the <S>function templates
instantiated in this way</S> <B>synthesized declarations</B> and all
of the non-template overloaded functions of the same name. The
<S>function template specializations</S> <B>synthesized
declarations</B> are treated like any other functions in the remainder
of overload resolution, except as explicitly noted in 13.3.3&nbsp;



 <A HREF="over.html#over.match.best">over.match.best</A>.

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="370"></A>
<H4>370.
  
Can <TT>#include &lt;...&gt;</TT> form be used other than for standard C++ headers?
</H4>
<B>Section: </B>16.2&nbsp;



 <A HREF="cpp.html#cpp.include">cpp.include</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>DR
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Beman Dawes
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>01 August 2002<BR>


<P>[Voted into WP at the October, 2006 meeting.]</P>

<P>The motivation for this issue is a desire to write portable programs which 
will work with any conforming implementation.</P>
<P>The C++ Standard (16.2&nbsp;



 <A HREF="cpp.html#cpp.include">cpp.include</A>) provides two forms of
<TT>#include</TT> directives, with the &lt;...&gt; form being described
(16.2&nbsp;



 <A HREF="cpp.html#cpp.include">cpp.include</A> paragraph 2) as "for a header", and
the "..." form (16.2&nbsp;



 <A HREF="cpp.html#cpp.include">cpp.include</A> paragraph 3) as
for "the source file" identified between the delimiters. When the 
standard uses the term "header", it often appears to be limiting
the term to apply to the Standard Library headers only. Users of the
standard almost always use the term "header" more broadly, to
cover all <TT>#include</TT>d source files, but 
particularly those containing interface declarations.</P>

<P>Headers, including source files, can be categorized according to
their origin and usage:</P>
<OL>
  <LI>C++ Standard Library headers (which aren't necessarily files).</LI>
  <LI>Other standard libraries such as the POSIX headers.</LI>
  <LI>Operating system API's such as <I>windows.h</I>.</LI>
  <LI>Third party libraries, such as Boost, ACE, or commercial offerings.</LI>
  <LI>Organization-wide "standard" header files, such as a company's <I>
  config.hpp</I>.</LI>
  <LI>A project's "public" header files, often shared by all
      developers working on the same project.</LI>
  <LI>A project or user's "private", "local", or
      "detail" headers, in the same directory or sub-directory
      as the compilation unit.</LI>
</OL>
<P>Existing practice varies widely, but it is fairly easy to find users 
advocating:</P>
<UL>
  <LI>For (1), Standard Library headers, use &lt;...&gt;. All others
      use "...".</LI>
  <LI>For (7),  use "...". All others use &lt;...&gt;.</LI>
  <LI>Draw a line somewhere below (1) and above (7), and use
      &lt;...&gt; above the line and "..." below.
      The exact location of the line may be based on a perception of
      how often the header involved changes; some "make" utilities
      use this to optimize builds.</LI>
</UL>
<P>Do any of the practices A, B, or C result in programs which can be rejected 
by a conforming implementation?</P>

<P>The first defect is that readers of the standard have not been
able to reach consensus on the answers to the above question.</P>

<P>A second possible defect is that if A, B, or C can be rejected by a 
conforming implementation, then the standard should be changed because would 
mean there is a wide variance between the standard and existing practice.</P>

<P>
<U>Matt Austern</U>:
I really only see two positions:</P>
<OL>
<LI>Implementations have some unspecified mechanism (copying
files to a magic directory, adding a magic flag,...) such that the
line <TT>#include &lt;foo&gt;</TT> results in textual inclusion of
the file foo.</LI>
<LI>Implementations are not required to have any mechanism for
getting <TT>#include &lt;foo&gt;</TT> to perform textual inclusion of an 
arbitrary file <TT>foo</TT>.  That form is reserved for standard
library headers only.</LI>
</OL>
<P>I agree that the standard should clarify which of those two is the
case (I imagine it'll hinge on finding one crucual sentence that
either says "implementation defined" or "unspecified"), but from
the standpoint of portability I don't see much difference between
the two.  I claim that, with either of those two interpretations, using
<TT>#include &lt;foo&gt;</TT> is already nonportable.</P>

<P>(Of course, I claim that almost anything having to do with headers,
including the <TT>#include "foo"</TT> form, is also nonportable.  In practice
there's wide variation in how compilers handle paths, especially
relative paths.)</P>

<P>
<U>Beman Dawes</U>:
The whole issue can be resolved by replacing "header" with "header or 
source file" in 16.2&nbsp;



 <A HREF="cpp.html#cpp.include">cpp.include</A> paragraph 2.
That will bring the standard into 
alignment with existing practice by both users and implementations.  
The "header and/or source file" wording is used at least three other 
places in the standard where otherwise there might be some confusion.</P>

<P>
<U>John Skaller</U>:
In light of Andrew Koenig's comments, this doesn't appear to be the case,
since the mapping of include names to file names is implementation defined,
and therefore source file inclusion cannot be made portable
within the ISO C/C++ standards (since that provision obviously cannot be
removed).</P>

<P>A possible idea is to create a binding standard, outside the
C/C++ ISO Standards, which specifies not only the path lookup
mechanism but also the translation from include names to file
names. Clearly that is OS dependent, encoding dependent, etc,
but there is no reason not to have a binding standard for Unix,
Windows, etc, and specify these bindings in such a way that
copying directories from one OS to the other can result in
programs working on both OS's.</P>

<P>
<U>Andy Koenig</U>:
An easier solution might be to specify a (presumably unbounded, or
bounded only by implementation capacity) collection of header-file
names that every implementation must make it possible for programs
to access somehow, without specifying exactly how.</P>

<P>
<B>Notes from October 2002 meeting:</B>
</P>

<P>This was discussed at some length.  While there was widespread
agreement that such inclusion is inherently implementation-dependent,
we agreed to try to add wording that would make it clear that
implementations are permitted (but not required) to allow inclusion
of files using the &lt;...&gt; form of <TT>#include</TT>.</P>

<P>
<B>Proposed resolution (April, 2005):</B>
</P>

<P>Change 16.2&nbsp;



 <A HREF="cpp.html#cpp.include">cpp.include</A> paragraph 7 from:</P>

<BLOCKQUOTE>

[<I>Example:</I> The most common uses of <TT>#include</TT> preprocessing
directives are as in the following:

<PRE>
    #include &lt;stdio.h&gt;
    #include "myprog.h"
</PRE>

&mdash;<I>end example</I>] 

</BLOCKQUOTE>

<P>to:</P>

<BLOCKQUOTE>

[<I>Note:</I> Although an implementation may provide a mechanism for
making arbitrary source files available to the <TT>&lt; &gt;</TT>
search, in general programmers should use the <TT>&lt; &gt;</TT> form
for headers provided with the implementation, and the <TT>" "</TT>
form for sources outside the control of the implementation. For
instance:

<PRE>
    #include &lt;stdio.h&gt;
    #include &lt;unistd.h&gt;
    #include "usefullib.h"
    #include "myprog.h"
</PRE>

&mdash;<I>end note</I>] 

</BLOCKQUOTE>

<P>
<B>Notes from October, 2005 meeting:</B>
</P>

<P>Some doubt was expressed as to whether the benefit of this
non-normative clarification outweighs the overall goal of synchronizing
clause 16 with the corresponding text in the C99 Standard.  As a
result, this issue is being left in &ldquo;review&rdquo; status to
allow further discussion.</P>

<P>
<B>Additional notes (October, 2006):</B>
</P>

<P>WG14 takes no position on this change.</P>

<BR>
<BR>
<BR>
<BR>
<HR>
<A NAME="WP Status"></A>
<H3>Issues with "WP" Status</H3>
<HR>
<A NAME="513"></A>
<H4>513.
  
Non-class &ldquo;most-derived&rdquo; objects
</H4>
<B>Section: </B>1.8&nbsp;



 <A HREF="intro.html#intro.object">intro.object</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Marc Schoolderman
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>20 Mar 2005<BR>


<P>[Voted into WP at April, 2006 meeting.]</P>

<P>The standard uses &ldquo;most derived object&rdquo; in some places
(for example, 1.3.3&nbsp;



 <A HREF="intro.html#defns.dynamic.type">defns.dynamic.type</A>, 5.3.5&nbsp;



 <A HREF="expr.html#expr.delete">expr.delete</A>) to refer to objects of both class and non-class
type. However, 1.8&nbsp;



 <A HREF="intro.html#intro.object">intro.object</A> only formally defines it for
objects of class type.</P>

<P>Possible fix: Change the wording in 1.8&nbsp;



 <A HREF="intro.html#intro.object">intro.object</A>
paragraph 4 from</P>

<BLOCKQUOTE>
an object of a most derived class type is called a most derived object
</BLOCKQUOTE>

<P>to</P>

<BLOCKQUOTE>
an object of a most derived class type, or of non-class type, is called
a most derived object
</BLOCKQUOTE>

<P>
<B>Proposed resolution (October, 2005):</B>
</P>

<P>Add the indicated words to 1.8&nbsp;



 <A HREF="intro.html#intro.object">intro.object</A> paragraph 4:</P>

<BLOCKQUOTE>

If a complete object, a data member (9.2&nbsp;



 <A HREF="class.html#class.mem">class.mem</A>), or
an array element is of class type, its type is considered the <I>most
derived</I> class, to distinguish it from the class type of any base
class subobject; an object of a most derived class type<B>, or of a
non-class type,</B> is called a <I>most derived object</I>.

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="362"></A>
<H4>362.
  
Order of initialization in instantiation units
</H4>
<B>Section: </B>2.1&nbsp;



 <A HREF="lex.html#lex.phases">lex.phases</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mark Mitchell
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>2 July 2002<BR>


<P>[Voted into WP at March 2004 meeting.]</P>

<P>Should this program do what its author obviously expects?  As far as
I can tell, the standard says that the point of instantiation for
Fib&lt;n-1&gt;::Value is the same as the point of instantiation as the
enclosing specialization, i.e., Fib&lt;n&gt;::Value.  What in the standard
actually says that these things get initialized in the right order?</P>
<PRE>
  template&lt;int n&gt;
  struct Fib { static int Value; };

  template &lt;&gt;
  int Fib&lt;0&gt;::Value = 0;

  template &lt;&gt;
  int Fib&lt;1&gt;::Value = 1;

  template&lt;int n&gt;
  int Fib&lt;n&gt;::Value = Fib&lt;n-1&gt;::Value + Fib&lt;n-2&gt;::Value;

  int f ()
  {
    return Fib&lt;40&gt;::Value;
  }
</PRE>
<P>
<U>John Spicer</U>:
My opinion is that the standard does not specify
the behavior of this program.
I thought there was a core issue related to this, but I could not find it.
The issue that I recall proposed tightening up the static initialization
rules to make more cases well defined.</P>

<P>Your comment about point of instantiation is correct, but I don't think that
really matters.  What matters is the order of execution of the initialization
code at execution time.  Instantiations don't really live in
"translation units"
according to the standard.  They live in "instantiation units", and the
handling of instantiation units in initialization is unspecified (which should
probably be another core issue).  See 2.1&nbsp;



 <A HREF="lex.html#lex.phases">lex.phases</A>
paragraph 8.</P>

<P>
<B>Notes from October 2002 meeting:</B>
</P>

<P>We discussed this and agreed that we really do mean the the order
is unspecified.  John Spicer will propose wording on handling of
instantiation units in initialization.</P>

<P>
<B>Proposed resolution (April 2003):</B>
</P>
<P>
TC1 contains the following text in 3.6.2&nbsp;



 <A HREF="basic.html#basic.start.init">basic.start.init</A>
paragraph 1:</P>

<BLOCKQUOTE>
Objects with static storage duration defined in namespace scope in the
same translation unit and dynamically initialized shall be initialized
in the order in which their definition appears in the translation
unit.
</BLOCKQUOTE>

<P>
This was revised by <A HREF="
     cwg_defects.html#270">issue 270</A> to read:</P>

<BLOCKQUOTE>
Dynamic initialization of an object is either ordered or unordered.
Explicit specializations and definitions
of class template static data members have ordered
initialization. Other class template static data member instances have
unordered initialization. Other objects defined in namespace scope
have ordered initialization. Objects defined within a single
translation unit and with ordered initialization shall be initialized
in the order of their definitions in the translation unit. The order
of initialization is unspecified for objects with unordered
initialization and for objects defined in different translation units.
</BLOCKQUOTE>

<P>
This addresses this issue but while reviewing this issue some
additional changes were suggested for the above wording:</P>

<BLOCKQUOTE>
Dynamic initialization of an object is either ordered or unordered.
<B>Definitions of explicitly specialized</B>
<S>Explicit specializations and definitions of</S>
class template static data members have ordered
initialization. Other class template static data member<B>s (i.e.,
implicitly or explicitly instantiated specializations)</B>
<S>instances</S> have
unordered initialization. Other objects defined in namespace scope
have ordered initialization. Objects defined within a single
translation unit and with ordered initialization shall be initialized
in the order of their definitions in the translation unit. The order
of initialization is unspecified for objects with unordered
initialization and for objects defined in different translation units.
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="261"></A>
<H4>261.
  
When is a deallocation function "used?"
</H4>
<B>Section: </B>3.2&nbsp;



 <A HREF="basic.html#basic.def.odr">basic.def.odr</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>7 Nov 2000<BR>


<P>[Moved to DR at October 2002 meeting.]</P>



<P>3.2&nbsp;



 <A HREF="basic.html#basic.def.odr">basic.def.odr</A> paragraph 2 says that a deallocation
function is "used" by a <I>new-expression</I> or
<I>delete-expression</I> appearing in a potentially-evaluated
expression.  3.2&nbsp;



 <A HREF="basic.html#basic.def.odr">basic.def.odr</A> paragraph 3 requires only that
"used" functions be defined.</P>

<P>This wording runs afoul of the typical implementation technique for
polymorphic <I>delete-expression</I>s in which the deallocation
function is invoked from the virtual destructor of the most-derived
class.  The problem is that the destructor must be defined, because
it's virtual, and if it contains an implicit reference to the
deallocation function, the deallocation function must also be defined,
even if there are no relevant <I>new-expression</I>s or
<I>delete-expression</I>s in the program.</P>

<P>For example:</P>

<PRE>
        struct B { virtual ~B() { } };

        struct D: B {
            void operator delete(void*);
            ~D() { }
        };
</PRE>

<P>Is it required that <TT>D::operator delete(void*)</TT> be defined,
even if no <TT>B</TT> or <TT>D</TT> objects are ever created or
deleted?</P>

<P>
<B>Suggested resolution:</B> Add the words "or if it is found by
the lookup at the point of definition of a virtual destructor
(12.4&nbsp;



 <A HREF="special.html#class.dtor">class.dtor</A>)" to the specification in 3.2&nbsp;



 <A HREF="basic.html#basic.def.odr">basic.def.odr</A> paragraph 2.</P>

<P>
<B>Notes from 04/01 meeting:</B>
</P>

<P>The consensus was in favor of requiring that any declared
non-placement <TT>operator delete</TT> member function be
defined if the destructor for the class is defined (whether
virtual or not), and similarly for a non-placement
<TT>operator new</TT> if a constructor is defined.</P>

<P>
<B>Proposed resolution (10/01):</B>
</P>

<P> In 3.2&nbsp;



 <A HREF="basic.html#basic.def.odr">basic.def.odr</A> paragraph 2, add the indicated text:
<BLOCKQUOTE>
An allocation or deallocation function for a class is
used by a new expression appearing in a potentially-evaluated
expression as specified in 5.3.4&nbsp;



 <A HREF="expr.html#expr.new">expr.new</A>
and 12.5&nbsp;



 <A HREF="special.html#class.free">class.free</A>.
A deallocation function for a class is used by a delete expression
appearing in a potentially-evaluated expression as specified in
5.3.5&nbsp;



 <A HREF="expr.html#expr.delete">expr.delete</A> and 12.5&nbsp;



 <A HREF="special.html#class.free">class.free</A>.
<B> A non-placement allocation or deallocation function for a
class is used by the definition of a constructor of that class.  A
non-placement deallocation function for a class is used by the
definition of the destructor of that class, or by being selected by
the lookup at
the point of definition of a virtual destructor (12.4&nbsp;



 <A HREF="special.html#class.dtor">class.dtor</A>).
[Footnote: An implementation is not required to call
allocation and deallocation functions from constructors or
destructors; however, this is a permissible implementation
technique.]</B>
</BLOCKQUOTE>
</P>

<BR>
<BR>
<HR>
<A NAME="289"></A>
<H4>289.
  
Incomplete list of contexts requiring a complete type
</H4>
<B>Section: </B>3.2&nbsp;



 <A HREF="basic.html#basic.def.odr">basic.def.odr</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>25 May 2001<BR>


<P>[Moved to DR at October 2002 meeting.]</P>

<P>3.2&nbsp;



 <A HREF="basic.html#basic.def.odr">basic.def.odr</A> paragraph 4 has a note listing the contexts
that require a class type to be complete.  It does not list use as a
base class as being one of those contexts.</P>

<P>
<B>Proposed resolution (10/01):</B>
</P>

<P>In 3.2&nbsp;



 <A HREF="basic.html#basic.def.odr">basic.def.odr</A> paragraph 4 add a new bullet at the
end of the note as the next-to-last bullet:
<UL>
<LI>
a class with a base class of type <TT>T</TT> is defined
(10&nbsp;



 <A HREF="derived.html#class.derived">class.derived</A>), or
</LI>
</UL>
</P>

<BR>
<BR>
<HR>
<A NAME="433"></A>
<H4>433.
  
Do elaborated type specifiers in templates inject into enclosing namespace scope?
</H4>
<B>Section: </B>3.3.1&nbsp;



 <A HREF="basic.html#basic.scope.pdecl">basic.scope.pdecl</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Daveed Vandevoorde
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>2 September 2003<BR>


<P>[Voted into WP at March 2004 meeting.]</P>



<P>Consider the following translation unit:</P>
<PRE>
  template&lt;class T&gt; struct S {
    void f(union U*);  // (1)
  };
  template&lt;class T&gt; void S&lt;T&gt;::f(union U*) {}  // (2)
  U *p;  // (3)
</PRE>
<P>Does (1) introduce U as a visible name in the surrounding
namespace scope?</P>

<P>If not, then (2) could presumably be an error since the
"union U" in that definition does not find the same type
as the declaration (1).</P>

<P>If yes, then (3) is OK too.  However, we have gone through
much trouble to allow template implementations that do not
pre-parse the template definitions, but requiring (1) to
be visible would change that.</P>

<P>A slightly different case is the following:</P>
<PRE>
  template&lt;typename&gt; void f() { union U *p; }
  U *q;  // Should this be valid?
</PRE>

<P>
<B>Notes from October 2003 meeting:</B>
</P>

<P>There was consensus that example 1 should be allowed.
(Compilers already parse declarations in templates; even MSVC++ 6.0
accepts this case.)  The vote was 7-2.</P>

<P>Example 2, on the other hand, is wrong; the union name goes
into a block scope anyway.</P>

<P>
<B>Proposed resolution:</B>
</P>

<P>
In 3.3.1&nbsp;



 <A HREF="basic.html#basic.scope.pdecl">basic.scope.pdecl</A>
change the second bullet of paragraph 5 as follows:</P>
<BLOCKQUOTE>
for an <I>elaborated-type-specifier</I> of the form
<PRE>
   class-key identifier
</PRE>
if the <I>elaborated-type-specifier</I> is used in the
<I>decl-specifier-seq</I> or <I>parameter-declaration-clause</I>
of a function defined in namespace scope, the identifier is declared
as a <I>class-name</I> in the namespace that contains the
declaration; otherwise, except as a friend declaration, the identifier
is declared in the smallest non-class, non-function-prototype scope
that contains the declaration. <B>[Note: These rules also apply within
templates.]</B> [Note: ...]
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="432"></A>
<H4>432.
  
Is injected class name visible in base class specifier list?
</H4>
<B>Section: </B>3.3.6&nbsp;



 <A HREF="basic.html#basic.scope.class">basic.scope.class</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Daveed Vandevoorde
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>29 August 2003<BR>


<P>[Voted into WP at March 2004 meeting.]</P>



<P>Consider the following example (inspired by a
question from comp.lang.c++.moderated):</P>
<PRE>
  template&lt;typename&gt; struct B {};
  template&lt;typename T&gt; struct D: B&lt;D&gt; {};
</PRE>
<P>Most (all?) compilers reject this code because
D is handled as a template name rather than as
the injected class name.</P>

<P>9&nbsp;



 <A HREF="class.html#class">class</A>/2 says that the injected class
name is "inserted into the scope of the class."</P>

<P>3.3.6&nbsp;



 <A HREF="basic.html#basic.scope.class">basic.scope.class</A>/1 seems to be the text
intended to describe
what "scope of a class" means, but it assumes that
every name in that scope was introduced using a
"declarator".  For an implicit declaration such
as the injected-class name it is not clear what
that means.</P>

<P>So my questions:</P>
<OL>
<LI>
Should the injected class name be available
in the base class specifiers?
<BLOCKQUOTE>
<U>John Spicer:</U>
I do not believe the injected class name should be available in the base 
specifier.  I think the semantics of injected class names should be as 
if a magic declaration were inserted after the opening "{" of the class 
definition.  The injected class name is a member of the class and 
members don't exist at the point where the base specifiers are scanned.
</BLOCKQUOTE>
</LI>
<LI>
Do you agree the wording should be clarified
whatever the answer to the first question? 
<BLOCKQUOTE>
<U>John Spicer:</U>
I believe the 3.3.6&nbsp;



 <A HREF="basic.html#basic.scope.class">basic.scope.class</A> wording should be
updated to reflect the fact that not all names come from declarators.
</BLOCKQUOTE>
</LI>
</OL>

<P>
<B>Notes from October 2003 meeting:</B>
</P>

<P>We agree with John Spicer's suggested answers above.</P>

<P>
<B>Proposed Resolution (October 2003):</B>
</P>

<P>
The answer to question 1 above is 
No and no change is required.</P>
<P>
For question 1, change 3.3.6&nbsp;



 <A HREF="basic.html#basic.scope.class">basic.scope.class</A>
paragraph 1 rule 1 to:</P>
<BLOCKQUOTE>
1) The potential scope of a name declared in a class consists not only of the 
declarative region following the name's <B>point of declaration</B>
<S>declarator</S>,
but also of all function
bodies, default arguments, and constructor <I>ctor-initializers</I>
in that class (including such things in nested classes).
The point of declaration of an <I>injected-class-name</I>
(clause 9&nbsp;



 <A HREF="class.html#class">class</A>) is 
immediately following the opening brace of the class definition.
</BLOCKQUOTE>
<P>(Note that this change overlaps a change in
<A HREF="
     cwg_defects.html#417">issue 417</A>.)</P>
<P>
Also change 3.3.1&nbsp;



 <A HREF="basic.html#basic.scope.pdecl">basic.scope.pdecl</A>
by adding a new paragraph 8 for the <I>injected-class-name</I> case:</P>
<BLOCKQUOTE>
The point of declaration for an <I>injected-class-name</I>
(clause 9&nbsp;



 <A HREF="class.html#class">class</A>) is
immediately following the opening brace of the class definition.
</BLOCKQUOTE>
<P>Alternatively this paragraph could be added after paragraph 5 and before the
two note paragraphs (i.e. it would become paragraph 5a).</P>

<BR>
<BR>
<HR>
<A NAME="139"></A>
<H4>139.
  
Error in <TT>friend</TT> lookup example
</H4>
<B>Section: </B>3.4.1&nbsp;



 <A HREF="basic.html#basic.lookup.unqual">basic.lookup.unqual</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>14 Jul 1999<BR>



<P>[Moved to DR at 10/01 meeting.]</P>

<P>The example in
3.4.1&nbsp;



 <A HREF="basic.html#basic.lookup.unqual">basic.lookup.unqual</A>
 paragraph 3 is
incorrect:</P>

<PRE>
    typedef int f;
    struct A {
        friend void f(A &amp;);
        operator int();
        void g(A a) {
            f(a);
        }
    };
</PRE>

Regardless of the resolution of other issues concerning the lookup
of names in <TT>friend</TT> declarations, this example is ill-formed
(the function and the typedef cannot exist in the same scope).

<P>One possible repair of the example would be to make <TT>f</TT>
a class with a constructor taking either <TT>A</TT> or <TT>int</TT>
as its parameter.</P>

<P>(See also issues
<A HREF="
     cwg_closed.html#95">95</A>,
<A HREF="
     cwg_defects.html#136">136</A>,
<A HREF="
     cwg_active.html#138">138</A>,
<A HREF="
     cwg_defects.html#143">143</A>,
<A HREF="
     cwg_closed.html#165">165</A>, and
<A HREF="
     cwg_defects.html#166">166</A>.)</P>

<P>
<B>Proposed resolution (04/01):</B>
</P>

<OL>

<LI>
<P>Change the example in 3.4.1&nbsp;



 <A HREF="basic.html#basic.lookup.unqual">basic.lookup.unqual</A>
paragraph 3 to read:</P>

<PRE>
    typedef int f;
    namespace N {
        struct A {
            friend int f(A &amp;);
            operator int();
            void g(A a) {
                int i = f(a);
                      // f is the typedef, not the friend function:
                      // equivalent to int(a)
            }
        };
    }
</PRE>
</LI>

<LI>
<P>Delete the sentence immediately following the example:</P>

<BLOCKQUOTE>

The expression <TT>f(a)</TT> is a <I>cast-expression</I>
equivalent to <TT>int(a)</TT>.

</BLOCKQUOTE>
</LI>

</OL>

<BR>
<BR>
<HR>
<A NAME="143"></A>
<H4>143.
  
Friends and Koenig lookup
</H4>
<B>Section: </B>3.4.2&nbsp;



 <A HREF="basic.html#basic.lookup.argdep">basic.lookup.argdep</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>21 Jul 1999<BR>



<P>[Moved to DR at 4/02 meeting.]</P>



<P>Paragraphs 1 and 2 of
3.4.2&nbsp;



 <A HREF="basic.html#basic.lookup.argdep">basic.lookup.argdep</A>
 say, in part,</P>

<BLOCKQUOTE>
When an unqualified name is used as the <I>postfix-expression</I>
in a function call
(5.2.2&nbsp;



 <A HREF="expr.html#expr.call">expr.call</A>
)... namespace-scope
friend function declarations
(11.4&nbsp;



 <A HREF="access.html#class.friend">class.friend</A>
) not otherwise
visible may be found... the set of declarations found
by the lookup of the function name [includes] the set
of declarations found in the... classes associated with
the argument types.
</BLOCKQUOTE>

The most straightforward reading of this wording is that if a function of
namespace scope (as opposed to a class member function) is
declared as a friend in a class, and that class is an
associated class in a function call, the friend function will
be part of the overload set, even if it is not visible to
normal lookup.

<P>Consider the following example:</P>

<PRE>
    namespace A {
	class S;
    };
    namespace B {
	void f(A::S);
    };
    namespace A {
	class S {
	    int i;
	    friend void B::f(S);
	};
    }
    void g() {
	A::S s;
	f(s); // should find B::f(A::S)
    }
</PRE>

This example would seem to satisfy the criteria from
3.4.2&nbsp;



 <A HREF="basic.html#basic.lookup.argdep">basic.lookup.argdep</A>
:
<TT>A::S</TT> is an associated class of the argument, and
<TT>A::S</TT> has a
friend declaration of the namespace-scope function
<TT>B::f(A::S)</TT>,
so Koenig lookup should include <TT>B::f(A::S)</TT> as part of the
overload set in the call.

<P>Another interpretation is that, instead of finding the friend
declarations in associated classes, one only looks for namespace-scope
functions, visible or invisible, in the namespaces of which the the
associated classes are members; the only use of the friend
declarations in the associated classes is to validate whether an
invisible function declaration came from an associated class or not
and thus whether it should be included in the overload set or not.
By this interpretation, the call <TT>f(s)</TT> in the example will
fail, because <TT>B::f(A::S)</TT> is not a member of namespace
<TT>A</TT> and thus is not found by the lookup.</P>

<P>
<B> Notes from 10/99 meeting:</B> The second interpretation
is correct.  The wording should be revised to make clear that Koenig
lookup works by finding "invisible" declarations in namespace scope
and not by finding <TT>friend</TT> declarations in associated
classes.</P>

<P>
<B>Proposed resolution (04/01):</B> The "associated classes"
are handled adequately under this interpretation by
3.4.2&nbsp;



 <A HREF="basic.html#basic.lookup.argdep">basic.lookup.argdep</A> paragraph 3, which describes the
lookup in the associated namespaces as including the friend
declarations from the associated classes.  Other mentions of the
associated classes should be removed or qualified to avoid the
impression that there is a lookup in those classes:</P>

<OL>

<LI>
<P>In 3.4.2&nbsp;



 <A HREF="basic.html#basic.lookup.argdep">basic.lookup.argdep</A>, change</P>

<BLOCKQUOTE>

When an unqualified name is used as the <I>postfix-expression</I>
in a function call (5.2.2&nbsp;



 <A HREF="expr.html#expr.call">expr.call</A>), other
namespaces not considered during the usual unqualified lookup
(3.4.1&nbsp;



 <A HREF="basic.html#basic.lookup.unqual">basic.lookup.unqual</A>) may be searched, and
namespace-scope friend function declarations
(11.4&nbsp;



 <A HREF="access.html#class.friend">class.friend</A>) not otherwise visible may be found.

</BLOCKQUOTE>

<P>to</P>

<BLOCKQUOTE>

When an unqualified name is used as the <I>postfix-expression</I>
in a function call (5.2.2&nbsp;



 <A HREF="expr.html#expr.call">expr.call</A>), other
namespaces not considered during the usual unqualified lookup
(3.4.1&nbsp;



 <A HREF="basic.html#basic.lookup.unqual">basic.lookup.unqual</A>) may be searched, and
<B>in those namespaces,</B>
namespace-scope friend function declarations
(11.4&nbsp;



 <A HREF="access.html#class.friend">class.friend</A>) not otherwise visible may be found.

</BLOCKQUOTE>

</LI>

<LI>
<P>In 3.4.2&nbsp;



 <A HREF="basic.html#basic.lookup.argdep">basic.lookup.argdep</A> paragraph 2, delete
the words <B>and classes</B> in the following two sentences:</P>

<BLOCKQUOTE>

If the ordinary unqualified lookup of the name finds the
declaration of a class member function, the associated namespaces
<B><S>and classes</S></B> are not considered.  Otherwise the
set of declarations found by the lookup of the function name is
the union of the set of declarations found using ordinary
unqualified lookup and the set of declarations found in the
namespaces <B><S>and classes</S></B> associated with the
argument types.

</BLOCKQUOTE>

</LI>

</OL>

<P>(See also issues
<A HREF="
     cwg_closed.html#95">95</A>,
<A HREF="
     cwg_defects.html#136">136</A>,
<A HREF="
     cwg_active.html#138">138</A>,
<A HREF="
     cwg_defects.html#139">139</A>,
<A HREF="
     cwg_closed.html#165">165</A>,
<A HREF="
     cwg_defects.html#166">166</A>, and
<A HREF="
     cwg_active.html#218">218</A>.)</P>
<BR>
<BR>
<HR>
<A NAME="403"></A>
<H4>403.
  
Reference to a type as a <I>template-id</I>
</H4>
<B>Section: </B>3.4.2&nbsp;



 <A HREF="basic.html#basic.lookup.argdep">basic.lookup.argdep</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>John Spicer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>18 Sep 2003<BR>


<P>[Voted into WP at March 2004 meeting.]</P>



<P>Spun off from <A HREF="
     cwg_closed.html#384">issue 384</A>.</P>

<P>3.4.2&nbsp;



 <A HREF="basic.html#basic.lookup.argdep">basic.lookup.argdep</A> says:
<BLOCKQUOTE>
If T is a template-id, its associated namespaces and classes are the
    namespace  in  which  the template is defined; for member templates,
    the member template's class; the namespaces and  classes  associated
    with  the types of the template arguments provided for template type
    parameters (excluding template template parameters); the  namespaces
    in  which  any  template  template  arguments  are  defined; and the
    classes in which any member  templates  used  as  template  template
    arguments  are  defined.   [Note: non-type template arguments do not
    contribute to the set of associated namespaces.  ]
</BLOCKQUOTE>
There is a problem with the term "is a template-id".  template-id
is a syntactic construct and you can't really talk about a type being a
template-id.  Presumably, this is intended to mean "If T is the type of a
class template specialization ...".</P>

<P>
<B>Proposed Resolution (October 2003):</B>
</P>

<P>
In 3.4.2&nbsp;



 <A HREF="basic.html#basic.lookup.argdep">basic.lookup.argdep</A>, paragraph 2, bullet 8, replace
<BLOCKQUOTE>
If T is a <I>template-id</I> ...
</BLOCKQUOTE>

with

<BLOCKQUOTE>
If T is a class template specialization ...
</BLOCKQUOTE>
</P>

<BR>
<BR>
<HR>
<A NAME="298"></A>
<H4>298.
  
<TT>T::x</TT> when <TT>T</TT> is cv-qualified
</H4>
<B>Section: </B>3.4.3.1&nbsp;



 <A HREF="basic.html#class.qual">class.qual</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Adamczyk
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>7 Jul 2001<BR>


<P>[Voted into WP at April 2003 meeting.]</P>

<P>Can a typedef <TT>T</TT> to a cv-qualified class type be used
in a qualified name <TT>T::x</TT>?</P>

<PRE>
    struct A { static int i; };
    typedef const A CA;
    int main () {
      CA::i = 0;  // Okay?
    }
</PRE>

<P>Suggested answer: Yes.  All the compilers I tried accept the test case.</P>

<P>
<B>Proposed resolution (10/01):</B>
</P>

<P>In 3.4.3.1&nbsp;



 <A HREF="basic.html#class.qual">class.qual</A> paragraph 1 add the indicated text:
<BLOCKQUOTE>
If the <I>nested-name-specifier</I> of a <I>qualified-id</I> nominates
a class,  the
name  specified  after  the  <I>nested-name-specifier</I> is looked up in the
scope of the  class  (10.2&nbsp;



 <A HREF="derived.html#class.member.lookup">class.member.lookup</A>),  except  for  the  cases
listed  below.   The  name shall represent one or more members of that
class or of one of its base classes (clause 10&nbsp;



 <A HREF="derived.html#class.derived">class.derived</A>). 
<B>If the <I>class-or-namespace-name</I> of the <I>nested-name-specifier</I>
names a cv-qualified class type, it nominates the underlying class
(the cv-qualifiers are ignored).</B>
</BLOCKQUOTE>
</P>

<P>
<B>Notes from 4/02 meeting:</B>
</P>

<P>There is a problem in that <I>class-or-namespace-name</I> does not
include typedef names for cv-qualified class types.  See
7.1.3&nbsp;



 <A HREF="dcl.html#dcl.typedef">dcl.typedef</A> paragraph 4:</P>

<P>
<B>Argument and text removed from proposed resolution
(October 2002):</B>
</P>

<P>
<B>7.1.3&nbsp;



 <A HREF="dcl.html#dcl.typedef">dcl.typedef</A> paragraph 5:</B>
</P>
<P>
Here's a good question: in this example, should <TT>X</TT>
be used as a name-for-linkage-purposes (FLP name)?
</P>
<PRE>
  typedef class { } const X;
</PRE>
<P>
Because a <I>type-qualifier</I> is parsed as a
<I>decl-specifier</I>, it isn't possible to declare cv-qualified
and cv-unqualified typedefs for a type in a single declaration.
Also, of course, there's no way to declare a typedef for the
cv-unqualified version of a type for which only a cv-qualified version
has a name.
So, in the above example, if <TT>X</TT> isn't used as the FLP name,
then there can be no FLP name.
Also note that a FLP name usually represents a parameter type, where
top-level cv-qualifiers are usually irrelevant anyway.
</P>
<P>
Data points: for the above example, Microsoft uses <TT>X</TT> as the
FLP name; GNU and EDG do not.
</P>
<P>
My recommendation: for consistency with the direction we're going on
this issue, for simplicity of description (e.g., "the first
<I>class-name</I> declared by the declaration"), and for (very
slightly) increased utility, I think Microsoft has this right.
</P>
<BLOCKQUOTE>
If the typedef declaration defines an unnamed class <B>type</B> (or
enum <B>type</B>), the first <I>typedef-name</I> declared by the
declaration to <S>be</S> <B>have</B> that <S>class</S> type
<S>(or enum type)</S> <B>or a cv-qualified version thereof</B>
is used to denote the class type (or enum type) for linkage purposes
only (3.5&nbsp;



 <A HREF="basic.html#basic.link">basic.link</A>).
[<I>Example:</I> ...
</BLOCKQUOTE>

<P>
<B>Proposed resolution (October 2002):</B>
</P>

<P>
<B>3.4.4&nbsp;



 <A HREF="basic.html#basic.lookup.elab">basic.lookup.elab</A> paragraphs 2 and 3:</B>
</P>
<P>
This sentence is deleted twice:
</P>
<BLOCKQUOTE>
...
<S>If this name lookup finds a <I>typedef-name</I>, the
<I>elaborated-type-specifier</I> is ill-formed.</S>
...
</BLOCKQUOTE>
<P>Note that the above changes are included in
N1376 as part of the resolution of <A HREF="
     cwg_defects.html#245">issue 245</A>.</P>

<P>
<B>5.1&nbsp;



 <A HREF="expr.html#expr.prim">expr.prim</A> paragraph 7:</B>
</P>
<P>
This is only a note, and it is at least incomplete (and quite possibly
inaccurate), despite (or because of) its complexity.
I propose to delete it.
</P>
<BLOCKQUOTE>
...
[<I>Note:</I> a <I>typedef-name</I> that names a class is a
<I>class-name</I> (9.1&nbsp;



 <A HREF="class.html#class.name">class.name</A>).
<S>Except as the <I>identifier</I> in the declarator for a constructor
or destructor definition outside of a class
<I>member-specification</I> (12.1&nbsp;



 <A HREF="special.html#class.ctor">class.ctor</A>,
12.4&nbsp;



 <A HREF="special.html#class.dtor">class.dtor</A>), a <I>typedef-name</I>
that names a class may be used in a <I>qualified-id</I> to refer to
a constructor or destructor.</S> ]
</BLOCKQUOTE>

<P>
<B>7.1.3&nbsp;



 <A HREF="dcl.html#dcl.typedef">dcl.typedef</A> paragraph 4:</B>
</P>
<P>
My first choice would have been to make this the primary statement about
the equivalence of <I>typedef-name</I> and <I>class-name</I>,
since the equivalence comes about as a result of a typedef declaration.
Unfortunately, references to <I>class-name</I> point to
9.1&nbsp;



 <A HREF="class.html#class.name">class.name</A>, so it
would seem that the primary statement should be there instead.
To avoid the possiblity of conflicts in the future, I propose to make
this a note.
</P>
<BLOCKQUOTE>
<B>[<I>Note:</I></B>
A <I>typedef-name</I> that names a class <B>type, or a cv-qualified
version thereof,</B> is <B>also</B> a <I>class-name</I>
(9.1&nbsp;



 <A HREF="class.html#class.name">class.name</A>).
If a <I>typedef-name</I> is used <S>following the
<I>class-key</I> in an <I>elaborated-type-specifier</I>
(7.1.5.3&nbsp;



 <A HREF="dcl.html#dcl.type.elab">dcl.type.elab</A>),
or in the <I>class-head</I> of a class declaration (9&nbsp;



 <A HREF="class.html#class">class</A>),
or is used as the <I>identifier</I> in the declarator for a
constructor or destructor declaration (12.1&nbsp;



 <A HREF="special.html#class.ctor">class.ctor</A>,
12.4&nbsp;



 <A HREF="special.html#class.dtor">class.dtor</A>),</S>
<B>to identify the subject of an <I>elaborated-type-specifier</I>
(7.1.5.3&nbsp;



 <A HREF="dcl.html#dcl.type.elab">dcl.type.elab</A>),
class declaration (clause 9&nbsp;



 <A HREF="class.html#class">class</A>),
constructor declaration (12.1&nbsp;



 <A HREF="special.html#class.ctor">class.ctor</A>),
or destructor declaration (12.4&nbsp;



 <A HREF="special.html#class.dtor">class.dtor</A>),</B>
the program is ill-formed.
<B>]</B>
[<I>Example:</I> ...
</BLOCKQUOTE>

<P>
<B>7.1.5.3&nbsp;



 <A HREF="dcl.html#dcl.type.elab">dcl.type.elab</A> paragraph 2:</B>
</P>
<P>
This is the only remaining (normative) statement that a
<I>typedef-name</I> can't be used in an
<I>elaborated-type-specifier</I>.
The reference to template <I>type-parameter</I> is deleted by the
resolution of <A HREF="
     cwg_defects.html#283">issue 283</A>.
</P>
<BLOCKQUOTE>
...
If the <I>identifier</I> resolves to a <I>typedef-name</I>
<S>or a template <I>type-parameter</I></S>, the
<I>elaborated-type-specifier</I> is ill-formed.
[<I>Note:</I> ...
</BLOCKQUOTE>

<P>
<B>8&nbsp;



 <A HREF="decl.html#dcl.decl">dcl.decl</A> grammar rule <I>declarator-id</I>:</B>
</P>
<P>
When I looked carefully into the statement of the rule prohibiting a
<I>typedef-name</I> in a constructor declaration, it appeared to me
that this grammar rule (inadvertently?) allows something that's always
forbidden semantically.
</P>
<BLOCKQUOTE>
<UL>
<I>declarator-id</I>:
<UL>
<I>id-expression</I>
<BR>
<TT>::</TT><I><SUB>opt</SUB> nested-name-specifier<SUB>opt</SUB>
<S>type-name</S> <B>class-name</B></I>
</UL>
</UL>
</BLOCKQUOTE>

<P>
<B>9.1&nbsp;



 <A HREF="class.html#class.name">class.name</A> paragraph 5:</B>
</P>
<P>
Unlike the prohibitions against appearing in an
<I>elaborated-type-specifier</I> or constructor or destructor
declarator, each of which was expressed more than once, the prohibition
against a <I>typedef-name</I> appearing in a <I>class-head</I>
was previously stated only in 7.1.3&nbsp;



 <A HREF="dcl.html#dcl.typedef">dcl.typedef</A>.
It seems to me that that prohibition belongs here instead.
Also, it seems to me important to clarify that a <I>typedef-name</I>
that is a <I>class-name</I> is still a <I>typedef-name</I>. 
Otherwise, the various prohibitions can be argued around easily, if
perversely ("But that
isn't a <I>typedef-name</I>, it's a <I>class-name</I>; it says
so right there in 9.1&nbsp;



 <A HREF="class.html#class.name">class.name</A>.")
</P>
<BLOCKQUOTE>
A <I>typedef-name</I> (7.1.3&nbsp;



 <A HREF="dcl.html#dcl.typedef">dcl.typedef</A>)
that names a class <B>type or a
cv-qualified version thereof</B> is
<B>also</B> a <I>class-name</I>, but shall not be used
<S>in an <I>elaborated-type-specifier</I>; see also
7.1.3&nbsp;



 <A HREF="dcl.html#dcl.typedef">dcl.typedef</A>.</S>
<B>as the <I>identifier</I> in a <I>class-head</I>.</B>
</BLOCKQUOTE>

<P>
<B>12.1&nbsp;



 <A HREF="special.html#class.ctor">class.ctor</A> paragraph 3:</B>
</P>
<P>
The new nonterminal references are needed to really nail down what we're
talking about here.
Otherwise, I'm just eliminating redundancy.
(A <I>typedef-name</I> that doesn't name a class type is no more
valid here than one that does.)
</P>
<BLOCKQUOTE>
<S>A <I>typedef-name</I> that names a class is a
<I>class-name</I> (7.1.3&nbsp;



 <A HREF="dcl.html#dcl.typedef">dcl.typedef</A>); however, a</S> <B>A</B>
<I>typedef-name</I> <S>that names a class</S> shall not be
used as the <S><I>identifier</I></S>
<B><I>class-name</I></B> in the <S>declarator</S>
<B><I>declarator-id</I></B> for a constructor declaration.
</BLOCKQUOTE>

<P>
<B>12.4&nbsp;



 <A HREF="special.html#class.dtor">class.dtor</A> paragraph 1:</B>
</P>
<P>
The same comments apply here as to 12.1&nbsp;



 <A HREF="special.html#class.ctor">class.ctor</A>.
</P>
<BLOCKQUOTE>
...
<S>A <I>typedef-name</I> that names a class is a
<I>class-name</I> (7.1.3); however, a</S> <B>A</B>
<I>typedef-name</I> <S>that names a class</S> shall not be
used as the <S><I>identifier</I></S> <B><I>class-name</I>
following the <TT>~</TT></B> in the declarator for a destructor
declaration.
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="318"></A>
<H4>318.
  
<TT>struct A::A</TT> should not name the constructor of <TT>A</TT>
</H4>
<B>Section: </B>3.4.3.1&nbsp;



 <A HREF="basic.html#class.qual">class.qual</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>John Spicer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>18 Oct 2001<BR>


<P>[Voted into WP at April 2003 meeting.]</P>

<P>A use of an injected-class-name in an elaborated-type-specifier
should not name the constructor of the class, but rather the class itself,
because in that context we know that we're looking for a type.
See <A HREF="
     cwg_defects.html#147">issue 147</A>.</P>

<P>
<B>Proposed Resolution (revised October 2002):</B>
</P>

<P> This clarifies the changes made in the TC for issue 147.</P>

<P>In 3.4.3.1&nbsp;



 <A HREF="basic.html#class.qual">class.qual</A> paragraph 1a replace:</P>
<BLOCKQUOTE>
If the <I>nested-name-specifier</I> nominates a class C, and the name
specified after the <I>nested-name-specifier</I>, when looked up in C, is the
injected class name of C (clause 9&nbsp;



 <A HREF="class.html#class">class</A>), the name is instead
considered to name the constructor of class C.
</BLOCKQUOTE>
<P> with </P>
<BLOCKQUOTE>
In a lookup in which the constructor is an acceptable lookup result,
if the <I>nested-name-specifier</I> nominates a class C and the name
specified after the <I>nested-name-specifier</I>, when looked up in C, is the
injected class name of C (clause 9&nbsp;



 <A HREF="class.html#class">class</A>), the name is
instead considered to name the constructor of class C.
[Note: For example, the constructor is not an acceptable lookup result in an
elaborated type specifier so the constructor would not be used in place
of the injected class name.]
</BLOCKQUOTE>

<P>Note that <A HREF="
     cwg_defects.html#263">issue 263</A> updates a part of the
same paragraph.</P>

<P>Append to the example:</P>
<PRE>
  struct A::A a2;  // object of type A
</PRE>

<BR>
<BR>
<HR>
<A NAME="400"></A>
<H4>400.
  
Using-declarations and the "struct hack"
</H4>
<B>Section: </B>3.4.3.2&nbsp;



 <A HREF="basic.html#namespace.qual">namespace.qual</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mark Mitchell
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>22 Jan 2003<BR>


<P>[Voted into WP at March 2004 meeting.]</P>

<P>Consider this code:</P>
<PRE>
  struct A { int i; struct i {}; };
  struct B { int i; struct i {}; };
  struct D : public A, public B { using A::i; void f (); };
  void D::f () { struct i x; }
</PRE>
<P>I can't find anything in the standard that says definitively what this 
means.  7.3.3&nbsp;



 <A HREF="dcl.html#namespace.udecl">namespace.udecl</A> says that a using-declaration shall
name "a member of a base class" -- but here we have two members, the
data member A::i and the class A::i.</P>

<P>Personally, I'd find it more attractive if this code did not work.  I'd 
like "using A::i" to mean "lookup A::i in the usual way and bind B::i to
that", which would mean that while "i = 3" would be valid in D::f,
"struct i x" would not be.  However, if there were no A::i data member,
then "A::i" would find the struct and the code in D::f would be valid.</P>

<P>
<U>John Spicer</U>:
I agree with you, but unfortunately the standard committee did not.</P>

<P>I remembered that this was discussed by the committee and that a
resolution was adopted that was different than what I hoped for, but I
had a hard time finding definitive wording in the standard.</P>

<P>I went back though my records and found the paper that proposed a
resolution and the associated committee motion that adopted the
proposed resolution The paper is N0905, and "option 1" from that paper
was adopted at the Stockholm meeting in July of 1996.  The resolution
is that "using A::i" brings in everything named i from A.</P>

<P>3.4.3.2&nbsp;



 <A HREF="basic.html#namespace.qual">namespace.qual</A> paragraph 2 was modified to
implement this resolution, but interestingly
that only covers the namespace case and not the class case.  I think
the class case was overlooked when the wording was drafted.  A core
issue should be opened to make sure the class case is handled
properly.</P>

<P>
<B>Notes from April 2003 meeting:</B>
</P>

<P>This is related to <A HREF="
     cwg_defects.html#11">issue 11</A>.
7.3.3&nbsp;



 <A HREF="dcl.html#namespace.udecl">namespace.udecl</A> paragraph 10 has an example
for namespaces.</P>

<P>
<B>Proposed resolution (October 2003):</B>
</P>

<P>Add a bullet to the end of 3.4.3.1&nbsp;



 <A HREF="basic.html#class.qual">class.qual</A>
paragraph 1:</P>
<UL>
<LI>the lookup for a name specified in a <I>using-declaration</I>
(7.3.3&nbsp;



 <A HREF="dcl.html#namespace.udecl">namespace.udecl</A>)
also finds class or enumeration names hidden within the same scope
(3.3.7&nbsp;



 <A HREF="basic.html#basic.scope.hiding">basic.scope.hiding</A>).
</LI>
</UL>
<P>Change the beginning of 7.3.3&nbsp;



 <A HREF="dcl.html#namespace.udecl">namespace.udecl</A> paragraph 4 from</P>
<BLOCKQUOTE>
A
<I>using-declaration</I>
used as a
<I>member-declaration</I>
shall refer to a member of a base class of the class being defined,
shall refer to a member of an anonymous union that is a member of a base class
of the class being defined, or
shall refer to an enumerator for an enumeration type that is a member of a base
class of the class being defined.
</BLOCKQUOTE>

<P>to</P>

<BLOCKQUOTE>
In a <I>using-declaration</I> used as a
<I>member-declaration</I>, the <I>nested-name-specifier</I>
shall name a base class of the class being defined.  Such a
<I>using-declaration</I> introduces the set of declarations found by member
name lookup (10.2&nbsp;



 <A HREF="derived.html#class.member.lookup">class.member.lookup</A>,
3.4.3.1&nbsp;



 <A HREF="basic.html#class.qual">class.qual</A>).
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="245"></A>
<H4>245.
  
Name lookup in <I>elaborated-type-specifier</I>s
</H4>
<B>Section: </B>3.4.4&nbsp;



 <A HREF="basic.html#basic.lookup.elab">basic.lookup.elab</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Jack Rouse
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>14 Sep 2000<BR>


<P>[Voted into WP at April 2003 meeting.]</P>



<P>I have some concerns with the description of name lookup for
elaborated type specifiers in 3.4.4&nbsp;



 <A HREF="basic.html#basic.lookup.elab">basic.lookup.elab</A>:</P>

<OL>

<LI>
<P>Paragraph 2 has some parodoxical statements concerning looking up
names that are simple identifers:</P>

<BLOCKQUOTE>
If the <I>elaborated-type-specifier</I> refers to an <I>enum-name</I>
and this lookup does not find a previously declared <I>enum-name</I>,
the <I>elaborated-type-specifier</I> is ill-formed. If the
<I>elaborated-type-specifier</I> refers to an <I>[sic]</I>
<I>class-name</I> and this lookup does not find a previously declared
<I>class-name</I>... the <I>elaborated-type-specifier</I> is a
declaration that introduces the <I>class-name</I> as described in
3.3.1&nbsp;



 <A HREF="basic.html#basic.scope.pdecl">basic.scope.pdecl</A>."
</BLOCKQUOTE>

<P>It is not clear how an <I>elaborated-type-specifier</I> can refer
to an <I>enum-name</I> or <I>class-name</I> given that the lookup does
not find such a name and that <I>class-name</I> and <I>enum-name</I>
are not part of the syntax of an <I>elaborated-type-specifier</I>.</P>
</LI>

<LI>
<P>The second sentence quoted above seems to suggest that the name found
will not be used if it is not a class name.  <I>typedef-name</I> names
are ill-formed due to the sentence preceding the quote.  If lookup
finds, for instance, an <I>enum-name</I> then a new declaration will
be created.  This differs from C, and from the enum case, and can have
surprising effects:</P>

<PRE>
    struct S {
       enum E {
           one = 1
       };
       class E* p;     // declares a global class E?
    };
</PRE>

<P>Was this really the intent?  If this is the case then some more
work is needed on 3.4.4&nbsp;



 <A HREF="basic.html#basic.lookup.elab">basic.lookup.elab</A>.  Note that the
section does not make finding a type template formal ill-formed, as is
done in 7.1.5.3&nbsp;



 <A HREF="dcl.html#dcl.type.elab">dcl.type.elab</A>.  I don't see anything that
makes a type template formal name a <I>class-name</I>.  So the example
in 7.1.5.3&nbsp;



 <A HREF="dcl.html#dcl.type.elab">dcl.type.elab</A> of <TT>friend class T;</TT> where
<TT>T</TT> is a template type formal would no longer be ill-formed
with this interpretation because it would declare a new class
<TT>T</TT>.</P> </LI>
</OL>

<P>(See also <A HREF="
     cwg_defects.html#254">issue 254</A>.)</P>

<P>
<B>Notes from the 4/02 meeting:</B>
</P>

<P>This will be consolidated with the changes for
<A HREF="
     cwg_defects.html#254">issue 254</A>.
See also <A HREF="
     cwg_defects.html#298">issue 298</A>.</P>

<P>
<B>Proposed resolution (October 2002):</B>
</P>

<P>As given in N1376=02-0034.  Note that the inserts and strikeouts in
that document do not display
correctly in all browsers; &lt;del&gt; --&gt; &lt;strike&gt;
and &lt;ins&gt; --&gt; &lt;b&gt;, and the
similar changes for the closing delimiters,
seem to do the trick.</P>

<BR>
<BR>
<HR>
<A NAME="254"></A>
<H4>254.
  
Definitional problems with <I>elaborated-type-specifier</I>s
</H4>
<B>Section: </B>3.4.4&nbsp;



 <A HREF="basic.html#basic.lookup.elab">basic.lookup.elab</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Clark Nelson
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>26 Oct 2000<BR>


<P>[Voted into WP at April 2003 meeting.]</P>

<OL>

<LI>
<P>The text in 3.4.4&nbsp;



 <A HREF="basic.html#basic.lookup.elab">basic.lookup.elab</A> paragraph 2 twice
refers to the possibility that an <I>elaborated-type-specifier</I>
might have the form</P>

<PRE>
        <I>class-key identifier</I> <TT>;</TT>
</PRE>

<P>However, the grammar for <I>elaborated-type-specifier</I> does
not include a semicolon.</P>
</LI>

<LI>
<P>In both 3.4.4&nbsp;



 <A HREF="basic.html#basic.lookup.elab">basic.lookup.elab</A> and
7.1.5.3&nbsp;



 <A HREF="dcl.html#dcl.type.elab">dcl.type.elab</A>, the text asserts that an
<I>elaborated-type-specifier</I> that refers to a <I>typedef-name</I>
is ill-formed.  However, it is permissible for the form of
<I>elaborated-type-specifier</I> that begins with <TT>typename</TT>
to refer to a <I>typedef-name</I>.</P>

<P>This problem is the result of adding the <TT>typename</TT> form
to the <I>elaborated-type-name</I> grammar without changing the
verbiage correspondingly.  It could be fixed either by updating the
verbiage or by moving the <TT>typename</TT> syntax into its own
production and referring to both nonterminals when needed.</P>
</LI>

</OL>

<P>(See also <A HREF="
     cwg_defects.html#180">issue 180</A>.  If this
issue is resolved in favor of a separate nonterminal in the
grammar for the <TT>typename</TT> forms, the wording in that
issue's resolution must be changed accordingly.)</P>

<P>
<B>Notes from 04/01 meeting:</B>
</P>

<P>The consensus was in favor of moving the <TT>typename</TT>
forms out of the <I>elaborated-type-specifier</I> grammar.</P>

<P>
<B>Notes from the 4/02 meeting:</B>
</P>

<P>This will be consolidated with the changes for
<A HREF="
     cwg_defects.html#245">issue 245</A>.</P>

<P>
<B>Proposed resolution (October 2002):</B>
</P>

<P>As given in N1376=02-0034.</P>

<BR>
<BR>
<HR>
<A NAME="381"></A>
<H4>381.
  
Incorrect example of base class member lookup
</H4>
<B>Section: </B>3.4.5&nbsp;



 <A HREF="basic.html#basic.lookup.classref">basic.lookup.classref</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Adamczyk
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>8 Nov 2002<BR>


<P>[Voted into WP at October 2004 meeting.]</P>

<P>The example in 3.4.5&nbsp;



 <A HREF="basic.html#basic.lookup.classref">basic.lookup.classref</A> paragraph 4
is wrong (see 11.2&nbsp;



 <A HREF="access.html#class.access.base">class.access.base</A> paragraph 5; the cast to the
naming class can't be done) and needs to be corrected.
This was noted when the final version of the algorithm for
<A HREF="
     cwg_defects.html#39">issue 39</A> was checked against it.</P>

<P>
<B>Proposed Resolution (October 2003):</B>
</P>

<P>Remove the entire note at the end of
3.4.5&nbsp;



 <A HREF="basic.html#basic.lookup.classref">basic.lookup.classref</A> paragraph 4, including the
entire example.</P>

<BR>
<BR>
<HR>
<A NAME="216"></A>
<H4>216.
  
Linkage of nameless class-scope enumeration types
</H4>
<B>Section: </B>3.5&nbsp;



 <A HREF="basic.html#basic.link">basic.link</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Daveed Vandevoorde
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>13 Mar 2000<BR>


<P>[Moved to DR at 10/01 meeting.]</P>



3.5&nbsp;



 <A HREF="basic.html#basic.link">basic.link</A> paragraph 4 says (among other things):

<BLOCKQUOTE>
A name having namespace scope has external linkage if it is the name of
<UL>
<LI>[...]</LI>

<LI>a named enumeration (7.2&nbsp;



 <A HREF="dcl.html#dcl.enum">dcl.enum</A>), or an
unnamed enumeration defined
in a typedef declaration in which the enumeration has the typedef
name for linkage purposes (7.1.3&nbsp;



 <A HREF="dcl.html#dcl.typedef">dcl.typedef</A>) </LI>
</UL>
</BLOCKQUOTE>

That prohibits for example:

<PRE>
    typedef enum { e1 } *PE;
    void f(PE) {}  // Cannot declare a function (with linkage) using a 
		   // type with no linkage.
</PRE>

<P>However, the same prohibition was not made for class scope types.  Indeed,
3.5&nbsp;



 <A HREF="basic.html#basic.link">basic.link</A> paragraph 5 says:</P>

<BLOCKQUOTE>
In addition, a member function, static data member, class or 
enumeration of class scope has external linkage if the name of the
class has external linkage.
</BLOCKQUOTE>

<P>That allows for:</P>

<PRE>
    struct S {
       typedef enum { e1 } *MPE;
       void mf(MPE) {}
    };
</PRE>

<P>My guess is that this is an unintentional consequence of
3.5&nbsp;



 <A HREF="basic.html#basic.link">basic.link</A> paragraph 5, but I would like confirmation
on that.</P>

<P>
<B>Proposed resolution:</B>
</P>

<P>Change text in 3.5&nbsp;



 <A HREF="basic.html#basic.link">basic.link</A> paragraph 5 from:</P>

<BLOCKQUOTE>

In addition, a member function, static data member, class or
enumeration of class scope has external linkage if the name of the
class has external linkage.

</BLOCKQUOTE>

to: 

<BLOCKQUOTE>

In addition, a member function, a static data member, a named class or
enumeration of class scope, or an unnamed class or enumeration defined
in a class-scope typedef declaration such that the class or
enumeration has the typedef name for linkage purposes
(7.1.3&nbsp;



 <A HREF="dcl.html#dcl.typedef">dcl.typedef</A>),
has external linkage if the name of the class has external linkage.

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="319"></A>
<H4>319.
  
Use of names without linkage in declaring entities with linkage
</H4>
<B>Section: </B>3.5&nbsp;



 <A HREF="basic.html#basic.link">basic.link</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Clark Nelson
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>29 Oct 2001<BR>


<P>[Voted into WP at October 2004 meeting.]</P>



<P>According to 3.5&nbsp;



 <A HREF="basic.html#basic.link">basic.link</A> paragraph 8,
"A name with no linkage ... shall not 
be used to declare an entity with linkage." This would appear to rule
out code such as:
<PRE>
  typedef struct {
    int i;
  } *PT;
  extern "C" void f(PT);
</PRE>
[likewise]
<PRE>
  static enum { a } e;
</PRE>
which seems rather harmless to me.</P>

<P>See <A HREF="
     cwg_closed.html#132">issue 132</A>, which dealt with a closely
related issue.</P>

<P>
<U>Andrei Iltchenko</U> submitted the same issue via comp.std.c++ on
17 Dec 2001:</P>

<P>Paragraph 8 of Section 3.5&nbsp;



 <A HREF="basic.html#basic.link">basic.link</A> contains the following
sentences: "A name with no linkage shall not be used to declare an
entity with linkage. If a declaration uses a typedef name, it is the
linkage of the type name to which the typedef refers that is
considered."</P>

<P>The problem with this wording is that it doesn't cover cases where the
type to which a typedef-name refers has no name. As a result it's not
clear whether, for example, the following program is well-formed:</P>
<PRE>
#include &lt;vector&gt;

int  main()
{
   enum  {   sz = 6u   };
   typedef int  (* aptr_type)[sz];
   typedef struct  data  {
      int   i,  j;
   }  * elem_type;
   std::vector&lt;aptr_type&gt;   vec1;
   std::vector&lt;elem_type&gt;   vec2;
}
</PRE>

<P>
<B>Suggested resolution:</B>
</P>

<P>My feeling is that the rules for whether or not a typedef-name used in
a declaration shall be treated as having or not having linkage ought
to be modelled after those for dependent types, which are explained in
14.6.2.1&nbsp;



 <A HREF="template.html#temp.dep.type">temp.dep.type</A>.</P>

<P>Add the following text at the end of Paragraph 8 of Section
3.5&nbsp;



 <A HREF="basic.html#basic.link">basic.link</A> and replace the following example:</P>
<BLOCKQUOTE>
In case of the type referred to by a typedef declaration not having a name,
the newly declared typedef-name has linkage if and only if its referred type
comprises no names of no linkage excluding local names that are eligible for
appearance in an integral constant-expression (5.19&nbsp;



 <A HREF="expr.html#expr.const">expr.const</A>).
[Note: if the referred
type contains a typedef-name that does not denote an unnamed class, the
linkage of that name is established by the recursive application of this
rule for the purposes of using typedef names in declarations.] [Example:
<PRE>
  void f()
  {
     struct A { int x; };        // no linkage
     extern A a;                 // ill-formed
     typedef A Bl
     extern B b;                 // ill-formed

     enum  {   sz = 6u   };
     typedef int  (* C)[sz];     // C has linkage because sz can
                                 // appear in a constant expression
  }
</PRE>
--end example.]
</BLOCKQUOTE>

<P>
<B>Additional issue (13 Jan 2002, from Andrei Iltchenko):</B>
</P>
<P>Paragraph 2 of Section 14.3.1&nbsp;



 <A HREF="template.html#temp.arg.type">temp.arg.type</A> is inaccurate and
unnecessarily prohibits a few important cases; it says "A local type, a type
with no linkage, an unnamed type or a type compounded from any of these
types shall not be used as a template-argument for a template-parameter."
The inaccuracy stems from the fact that it is not a type but its name that
can have a linkage.</P>

<P>For example based on the current wording of 14.3.1&nbsp;



 <A HREF="template.html#temp.arg.type">temp.arg.type</A>,
the following example is ill-formed.</P>
<PRE>
  #include &lt;vector&gt;
  struct  data  {
    int   i,  j;
  };
  int  main()
  {
    enum  {   sz = 6u   };
    std::vector&lt;int(*)[sz]&gt;   vec1; // The types 'int(*)[sz]' and 'data*'
    std::vector&lt;data*&gt;        vec2; // have no names and are thus illegal
                                    // as template type arguments.
  }
</PRE>

<P>
<B>Suggested resolution:</B>
</P>
<P>Replace the whole second paragraph of Section 14.3.1&nbsp;



 <A HREF="template.html#temp.arg.type">temp.arg.type</A>
with the following wording:</P>
<BLOCKQUOTE>
A type whose name does not have a linkage or a type compounded from any such
type shall not be used as a template-argument for a template-parameter. In
case of a type <TT>T</TT> used as a template type argument not having a name,
<TT>T</TT>
constitutes a valid template type argument if and only if the name of an
invented typedef declaration referring to <TT>T</TT> would have linkage;
see 3.5.
[Example:
<PRE>
  template &lt;class T&gt; class X { /* ... */ };
  void f()
  {
    struct S { /* ... */ };
    enum  {   sz = 6u   };

    X&lt;S&gt; x3;                     // error: a type name with no linkage
                                 // used as template-argument
    X&lt;S*&gt; x4;                    // error: pointer to a type name with
                                 // no linkage used as template-argument
    X&lt;int(*)[sz]&gt; x5;            // OK: since the name of typedef int
                                 // (*pname)[sz] would have linkage
  }
</PRE>
--end example] [Note: a template type argument may be an incomplete type
(3.9&nbsp;



 <A HREF="basic.html#basic.types">basic.types</A>).]
</BLOCKQUOTE>

<P>
<B>Proposed resolution:</B>
</P>

<P>This is resolved by the changes for
<A HREF="
     cwg_defects.html#389">issue 389</A>.  The present issue was moved back to
Review status in February 2004 because 389 was moved back to Review.</P>

<BR>
<BR>
<HR>
<A NAME="389"></A>
<H4>389.
  
Unnamed types in entities with linkage
</H4>
<B>Section: </B>3.5&nbsp;



 <A HREF="basic.html#basic.link">basic.link</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Daveed Vandevoorde
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>31 Oct 2002<BR>


<P>[Voted into WP at October 2004 meeting.]</P>



<P>3.5&nbsp;



 <A HREF="basic.html#basic.link">basic.link</A> paragraph 8 says (among other things):</P>
<BLOCKQUOTE>
A name with no linkage (notably, the name of a class or enumeration 
declared in a local scope (3.3.2&nbsp;



 <A HREF="basic.html#basic.scope.local">basic.scope.local</A>)) shall not
be used to declare an entity with linkage.
If a declaration uses a typedef name, it is the linkage of the type 
name to which the typedef refers that is considered.
</BLOCKQUOTE>

<P>I would expect this to catch situations such as the following:</P>
<PRE>
  // File 1:
  typedef struct {} *UP;
  void f(UP) {}

  // File 2:
  typedef struct {} *UP; // Or: typedef struct {} U, *UP;
  void f(UP);
</PRE>
<P>The problem here is that most implementations must generate the same 
mangled name
for "f" in two translation units.  The quote from the standard above 
isn't quite
clear, unfortunately: There is no type name to which the typedef refers.</P>

<P>A related situation is the following:
<PRE>
  enum { no, yes } answer;
</PRE>
The variable "answer" is declared as having external linkage, but it is 
declared
with an unnamed type.  Section 3.5&nbsp;



 <A HREF="basic.html#basic.link">basic.link</A>
talks about the linkage of <I>names</I>, however,
and does therefore not prohibit this.  There is no implementation issue 
for most
compilers because they do not ordinarily mangle variable names, but I 
believe
the intent was to allow that implementation technique.</P>

<P>Finally, these problems are much less relevant when declaring names 
with internal
linkage.  For example, I would expect there to be few problems with:</P>
<PRE>
  typedef struct {} *UP;
  static void g(UP);
</PRE>
<P>I recently tried to interpret 3.5&nbsp;



 <A HREF="basic.html#basic.link">basic.link</A> paragraph 8
with the assumption that types with no names
have no linkage.  Surprisingly, this resulted in many diagnostics on 
variable declarations (mostly like "answer" above).</P>

<P>I'm pretty sure the standard needs clarifying words in this matter, but 
which way should it go?</P>

<P>See also <A HREF="
     cwg_defects.html#319">issue 319</A>.</P>

<P>
<B>Notes from April 2003 meeting:</B>
</P>

<P>There was agreement that this check is not needed for variables
and functions with extern "C" linkage, and a change there is
desirable to allow use of legacy C headers.  The check is also not needed for
entities with internal linkage, but there was no strong sentiment
for changing that case.</P>

<P>We also considered relaxing this requirement for extern "C++"
variables but decided that we did not want to change that case.</P>

<P>We noted that if extern "C" functions are allowed an additional
check is needed when such functions are used as arguments in calls
of function templates.  Deduction will put the type of the extern "C"
function into the type of the template instance, i.e., there would
be a need to mangle the name of an unnamed type.  To plug that hole
we need an additional requirement on the template created in
such a case.</P>

<P>
<B>Proposed resolution (April 2003, revised slightly October 2003
and March 2004):</B>
</P>

<P>In 3.5&nbsp;



 <A HREF="basic.html#basic.link">basic.link</A> paragraph 8, change</P>
<BLOCKQUOTE>
A name with no linkage (notably, the name of a class or enumeration
declared in a local scope (3.3.2&nbsp;



 <A HREF="basic.html#basic.scope.local">basic.scope.local</A>))
shall not be used to declare an
entity with linkage.  If a declaration uses a typedef name, it is
the linkage of the type name to which the typedef refers that is
considered.
</BLOCKQUOTE>
<P>to</P>
<BLOCKQUOTE>
A type is said to have linkage if and only if
<UL>
<LI>
it is a class or enumeration type that is named (or has a name for
linkage purposes (7.1.3&nbsp;



 <A HREF="dcl.html#dcl.typedef">dcl.typedef</A>))
and the name has linkage; or
</LI>
<LI>
it is a specialization of a class template (14&nbsp;



 <A HREF="template.html#temp">temp</A>)
[Footnote: a class template always has external linkage, and
the requirements of 14.3.1&nbsp;



 <A HREF="template.html#temp.arg.type">temp.arg.type</A>
and 14.3.2&nbsp;



 <A HREF="template.html#temp.arg.nontype">temp.arg.nontype</A>
ensure that the template arguments will also have appropriate linkage]; or
</LI>
<LI>
it is a fundamental type (3.9.1&nbsp;



 <A HREF="basic.html#basic.fundamental">basic.fundamental</A>); or
</LI>
<LI>
it is a compound type (3.9.2&nbsp;



 <A HREF="basic.html#basic.compound">basic.compound</A>)
other than a class or enumeration,
compounded exclusively from types that have linkage; or
</LI>
<LI>
it is a cv-qualified (3.9.3&nbsp;



 <A HREF="basic.html#basic.type.qualifier">basic.type.qualifier</A>)
version of a type that has linkage.
</LI>
</UL>
A type without linkage shall not be used as the type of a variable or
function with linkage, unless the variable or function has extern "C"
linkage (7.5&nbsp;



 <A HREF="dcl.html#dcl.link">dcl.link</A>).
[<I>Note:</I> in other words, a type without linkage contains
a class or enumeration that cannot be named outside
of its translation unit.  An entity with external linkage
declared using such a type could not correspond to any other entity
in another translation unit of the program and is thus not permitted.
Also note that classes with linkage may contain members whose types do
not have linkage, and that typedef names are ignored in the determination of
whether a type has linkage.]
</BLOCKQUOTE>
<P>Change 14.3.1&nbsp;



 <A HREF="template.html#temp.arg.type">temp.arg.type</A> paragraph 2 from (note:
this is the wording as updated by <A HREF="
     cwg_defects.html#62">issue 62</A>)</P>
<BLOCKQUOTE>
The following types shall not be used as a <I>template-argument</I>
for a template <I>type-parameter</I>:

<UL>

<LI>a type whose name has no linkage</LI>

<LI>an unnamed class or enumeration type that has no name for
linkage purposes (7.1.3&nbsp;



 <A HREF="dcl.html#dcl.typedef">dcl.typedef</A>)</LI>

<LI>a cv-qualified version of one of the types in this list</LI>

<LI>a type created by application of declarator operators to one
of the types in this list</LI>

<LI>a function type that uses one of the types in this list</LI>

</UL>
</BLOCKQUOTE>
<P>to</P>
<BLOCKQUOTE>
A type without linkage (3.5&nbsp;



 <A HREF="basic.html#basic.link">basic.link</A>)
shall not be used as a <I>template-argument</I>
for a template <I>type-parameter</I>.
</BLOCKQUOTE>

<P>Once this issue is ready, <A HREF="
     cwg_defects.html#319">issue 319</A>
should be moved back to ready as well.</P>

<BR>
<BR>
<HR>
<A NAME="474"></A>
<H4>474.
  
Block-scope <TT>extern</TT> declarations in namespace members
</H4>
<B>Section: </B>3.5&nbsp;



 <A HREF="basic.html#basic.link">basic.link</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Daveed Vandevoorde
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>23 Jul 2004<BR>


<P>[Voted into WP at October 2005 meeting.]</P>



<P>Consider the following bit of code:</P>

<PRE>
    namespace N {
      struct S {
        void f();
      };
    }
    using namespace N;
    void S::f() {
      extern void g();  // ::g or N::g?
    }
</PRE>

<P>In 3.5&nbsp;



 <A HREF="basic.html#basic.link">basic.link</A> paragraph 7 the Standard says
(among other things),</P>

<BLOCKQUOTE>
When a block scope declaration of an entity with linkage is not
found to refer to some other declaration, then that entity is a
member of the innermost enclosing namespace.
</BLOCKQUOTE>

<P>The question then is whether <TT>N</TT> is an &ldquo;enclosing
namespace&rdquo; for the local declaration of <TT>g()</TT>?</P>

<P>
<B>Proposed resolution (October 2004):</B>
</P>

<P>Add the following text as a new paragraph at the end of
7.3.1&nbsp;



 <A HREF="dcl.html#namespace.def">namespace.def</A>:</P>

<BLOCKQUOTE>
The <I>enclosing namespaces</I> of a declaration are those
namespaces in which the declaration lexically appears, except for
a redeclaration of a namespace member outside its original
namespace (e.g., a definition as specified in 7.3.1.2&nbsp;



 <A HREF="dcl.html#namespace.memdef">namespace.memdef</A>). Such a redeclaration has the same enclosing
namespaces as the original declaration. [<I>Example:</I>

<PRE>
  namespace Q {
    namespace V {
      void f(); //<SPAN STYLE="font-family:Times"><I> enclosing namespaces are the global namespace, </I></SPAN>Q<SPAN STYLE="font-family:Times"><I>, and </I></SPAN>Q::V
      class C { void m(); };
    }
    void V::f() { //<SPAN STYLE="font-family:Times"><I> enclosing namespaces are the global namespace, </I></SPAN>Q<SPAN STYLE="font-family:Times"><I>, and </I></SPAN>Q::V
      extern void h(); //<SPAN STYLE="font-family:Times"><I> ... so this declares </I></SPAN>Q::V::h
    }
    void V::C::m() { //<SPAN STYLE="font-family:Times"><I> enclosing namespaces are the global namespace, </I></SPAN>Q<SPAN STYLE="font-family:Times"><I>, and </I></SPAN>Q::V
    }
  }
</PRE>

<P>&mdash;<I>end example</I>]</P>
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="270"></A>
<H4>270.
  
Order of initialization of static data members of class templates
</H4>
<B>Section: </B>3.6.2&nbsp;



 <A HREF="basic.html#basic.start.init">basic.start.init</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Jonathan H. Lundquist
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>9 Feb 2001<BR>


<P>[Moved to DR at 4/02 meeting.]</P>

<P>The Standard does not appear to address how the rules for order
of initialization apply to static data members of class templates.</P>

<P>
<U>Suggested resolution</U>: Add the following verbiage to either
3.6.2&nbsp;



 <A HREF="basic.html#basic.start.init">basic.start.init</A> or 9.4.2&nbsp;



 <A HREF="class.html#class.static.data">class.static.data</A>:</P>

<BLOCKQUOTE>

Initialization of static data members of class templates shall be
performed during the initialization of static data members for the
first translation unit to have static initialization performed for
which the template member has been instantiated.  This requirement
shall apply to both the static and dynamic phases of initialization.

</BLOCKQUOTE>

<P>
<B>Notes from 04/01 meeting:</B>
</P>

<P>Enforcing an order of initialization on static data members of
class templates will result in substantial overhead on access to such
variables. The problem is that the initialization be required as the
result of instantiation in a function used in the initialization of a
variable in another translation unit. In current systems, the order of
initialization of static data data members of class templates is not
predictable. The proposed resolution is to state that the order of
initialization is undefined.</P>

<P>
<B>Proposed resolution (04/01, updated slightly 10/01):</B>
</P>

<P>Replace the following sentence in 3.6.2&nbsp;



 <A HREF="basic.html#basic.start.init">basic.start.init</A>
paragraph 1:</P>

<BLOCKQUOTE>

Objects with static storage duration defined in namespace scope in the
same translation unit and dynamically initialized shall be initialized
in the order in which their definition appears in the translation
unit.

</BLOCKQUOTE>

<P>with</P>

<BLOCKQUOTE>

Dynamic initialization of an object is either ordered or unordered.
Explicit specializations and definitions
of class template static data members have ordered
initialization. Other class template static data member instances have
unordered initialization. Other objects defined in namespace scope
have ordered initialization. Objects defined within a single
translation unit and with ordered initialization shall be initialized
in the order of their definitions in the translation unit. The order
of initialization is unspecified for objects with unordered
initialization and for objects defined in different translation units.

</BLOCKQUOTE>

<P>
<I>Note that this wording is further updated by
<A HREF="
     cwg_defects.html#362">issue 362</A>.</I>
</P>

<P>
<B>Note (07/01):</B>
</P>

<P>
<U>Brian McNamara</U> argues against the proposed
resolution.  The following excerpt captures the central point of
a long message on comp.std.c++:</P>

<BLOCKQUOTE>
I have a class for representing linked lists which looks something like
<PRE>
    template &lt;class T&gt;
    class List {
       ...  static List&lt;T&gt;* sentinel; ...
    };
 
    template &lt;class T&gt;
    List&lt;T&gt;* List&lt;T&gt;::sentinel( new List&lt;T&gt; ); // static member definition
</PRE>
<P>The sentinel list node is used to represent "nil" (the null pointer
cannot be used with my implementation, for reasons which are immaterial
to this discussion).  All of the List's non-static member functions and
constructors depend upon the value of the sentinel.  Under the proposed
resolution for issue #270, Lists cannot be safely instantiated before
main() begins, as the sentinel's initialization is "unordered".</P>

<P>(Some readers may propose that I should use the "singleton pattern" in the
List class.  This is undesirable, for reasons I shall describe at the
end of this post at the location marked "[*]".  For the moment, indulge
me by assuming that "singleton" is not an adequate solution.)</P>

<P>Though this is a particular example from my own experience, I believe it
is representative of a general class of examples.  It is common to use
static data members of a class to represent the "distinguished values"
which are important to instances of that class.  It is imperative that
these values be initialized before any instances of the class are
created, as the instances depend on the values.</P>
</BLOCKQUOTE>

<P>In a comp.std.c++ posting on 28 Jul 2001, Brian McNamara proposes
the following alternative resolution:</P>

<P>Replace the following sentence in 3.6.2&nbsp;



 <A HREF="basic.html#basic.start.init">basic.start.init</A>
paragraph 1:</P>
<BLOCKQUOTE>
Objects with static storage duration defined in namespace scope in
the same translation unit and dynamically initialized shall be
initialized in the order in which their definition appears in the
translation unit.
</BLOCKQUOTE>
with
<BLOCKQUOTE>
Objects with static storage duration defined in namespace scope 
shall be initialized in the order described below.
</BLOCKQUOTE>
and then after paragraph 1, add this text:
<BLOCKQUOTE>
Dynamic initialization is either ordered or quasi-ordered. Explicit
specializations of class template static data members have ordered
initialization. Other class template static data member instances have
quasi-ordered initialization. All other objects defined in namespace
scope have ordered initialization.  The order of initialization is
specified as follows:
<UL>
<LI>
Objects that are defined within a single translation unit and 
that have ordered initialization shall be initialized in the
order of their definitions in the translation unit.
</LI>
<LI>
Objects that are defined only within a single translation unit 
and that have quasi-ordered initialization shall also be
initialized in the order of their definitions in the translation
unit -- that is, as though these objects had ordered initialization.
</LI>
<LI>
Objects that are defined within multiple translation units (which,
therefore, must have quasi-ordered initialization) shall be
initialized as follows: in exactly one translation unit
(<I>which</I> one is unspecified), the object shall be treated as
though it has ordered initialization; in the other translation
units which define the object, the object will be initialized
before all other objects that have ordered initialization in
those translation units.
</LI>
<LI>
For any two objects, "X" and "Y", with static storage duration 
and defined in namespace scope, if the previous bullets do not
imply a relationship for the initialization ordering between "X"
and "Y", then the relative initialization order of these objects
is unspecified.
</LI>
</UL>
</BLOCKQUOTE>
along with a non-normative note along the lines of
<BLOCKQUOTE>
[ Note: The intention is that translation units can each be compiled
separately with no knowledge of what objects may be re-defined in
other translation units.  Each translation unit can contain a method
which initializes all objects (both quasi-ordered and ordered) as
though they were ordered.  When these translation units are linked
together to create an executable program, all of these objects can
be initialized by simply calling the initialization methods (one
from each translation unit) in any order.  Quasi-ordered objects
require some kind of guard to ensure that they are not initialized
more than once (the first attempt to initialize such an object
should succeed; any subsequent attempts should simply be ignored). ]
</BLOCKQUOTE>

<P>
<U>Erwin Unruh</U> replies:
There is a point which is not mentioned with this posting.
It is the cost for implementing the scheme. It requires that each
static template variable is instantiated in ALL translation units
where it is used. There has to be a flag for each of these variables
and this flag has to be checked in each TU where the instantiation
took place.</P>

<P>I would reject this idea and stand with the proposed resolution of
issue 270.</P>

<P>There just is no portable way to ensure the "right" ordering of
construction.</P>

<P>
<B>Notes from 10/01 meeting:</B>
</P>

<P>The Core Working Group reaffirmed its previous decision.</P>

<BR>
<BR>
<HR>
<A NAME="441"></A>
<H4>441.
  
Ordering of static reference initialization
</H4>
<B>Section: </B>3.6.2&nbsp;



 <A HREF="basic.html#basic.start.init">basic.start.init</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>1 Dec 2003<BR>


<P>[Voted into WP at April 2005 meeting.]</P>



<P>
I have a couple of questions about 3.6.2&nbsp;



 <A HREF="basic.html#basic.start.init">basic.start.init</A>,
"Initialization of
non-local objects."  I believe I recall some discussion of
related topics, but I can't find anything relevant in the issues
list.
</P>

<P>The first question arose when I discovered that different
implementations treat reference initialization differently.
Consider, for example, the following (namespace-scope) code:
<PRE>
  int i;
  int&amp; ir = i;
  int* ip = &amp;i;
</PRE>
Both initializers, "i" and "&amp;i", are constant expressions, per
5.19&nbsp;



 <A HREF="expr.html#expr.const">expr.const</A> paragraph 4-5 (a reference constant expression and
an address constant
expression, respectively).  Thus, both initializations are
categorized as static initialization, according to
3.6.2&nbsp;



 <A HREF="basic.html#basic.start.init">basic.start.init</A> paragraph 1:
<BLOCKQUOTE>
    Zero-initialization and initialization with a constant
    expression are collectively called static initialization; all
    other initialization is dynamic initialization.
</BLOCKQUOTE>
</P>
<P>However, that does not mean that both ir and ip must be
initialized at the same time:
<BLOCKQUOTE>
    Objects of POD types (3.9) with static storage duration
    initialized with constant expressions (5.19) shall be
    initialized before any dynamic initialization takes place.
</BLOCKQUOTE>
</P>
<P>Because "int&amp;" is not a POD type, there is no requirement that it
be initialized before dynamic initialization is performed, and
implementations differ in this regard.  Using a function called
during dynamic initialization to print the values of "ip" and
"&amp;ir", I found that g++, Sun, HP, and Intel compilers initialize
ir before dynamic initialization and the Microsoft compiler does
not.  All initialize ip before dynamic initialization.  I believe
this is conforming (albeit inconvenient :-) behavior.
</P>

<P>So, my first question is whether it is intentional that a
reference of static duration, initialized with a reference
constant expression, need not be initialized before dynamic
initialization takes place, and if so, why?</P>

<P>The second question is somewhat broader.  As
3.6.2&nbsp;



 <A HREF="basic.html#basic.start.init">basic.start.init</A> is currently
worded, it appears that there are <U>no</U> requirements on when ir is
initialized.  In fact, there is a whole category of objects --
non-POD objects initialized with a constant expression -- for
which no ordering is specified.  Because they are categorized as
part of "static initialization," they are not subject to the
requirement that they "shall be initialized in the order in which
their definition appears in the translation unit."  Because they
are not POD types, they are not required to be initialized before
dynamic initialization occurs.  Am I reading this right?</P>

<P>My preference would be to change
3.6.2&nbsp;



 <A HREF="basic.html#basic.start.init">basic.start.init</A> paragraph 1 so that 1) references
are treated like POD objects with respect to initialization, and
2) "static initialization" applies only to POD objects and
references.  Here's some sample wording to illustrate:</P>

<P>
<B>Suggested resolution:</B>
</P>
<BLOCKQUOTE>
    Objects with static storage duration (3.7.1) shall be
    zero-initialized (8.5) before any other initialization takes
    place.  Initializing a reference, or an object of POD
    type, of static storage duration with a constant expression
    (5.19) is called constant initialization.  Together,
    zero-initialization and constant initialization are called
    static initialization; all other initialization is dynamic
    initialization.  Static initialization shall be performed
    before any dynamic initialization takes place.  [Remainder
    unchanged.]
</BLOCKQUOTE>

<P>
<B>Proposed Resolution:</B>
</P>

<P>Change 3.6.2&nbsp;



 <A HREF="basic.html#basic.start.init">basic.start.init</A> paragraph 1 as follows:
</P>
<BLOCKQUOTE>
Objects with static storage duration (3.7.1) shall be
zero-initialized (8.5) before any other initialization takes
place. <B>Initializing a reference, or an object of POD type, of
static storage duration with a constant expression (5.19) is
called <I>constant initialization</I>.  Together,
zero-initialization and constant initialization are
</B><S>Zero-initialization and initialization with a
constant expression are collectively</S> called <I>static
initialization</I>; all other initialization is <I>dynamic
initialization</I>. <B>Static initialization shall be performed
</B><S>Objects of POD types (3.9) with static storage
duration initialized with constant expressions (5.19) shall be
initialized</S> before any dynamic initialization takes
place.
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="348"></A>
<H4>348.
  
<TT>delete</TT> and user-written deallocation functions
</H4>
<B>Section: </B>3.7.3.2&nbsp;



 <A HREF="basic.html#basic.stc.dynamic.deallocation">basic.stc.dynamic.deallocation</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Ruslan Abdikeev
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>1 April 2002<BR>


<P>[Voted into WP at October 2005 meeting.]</P>

<P>Standard is clear on behaviour of default allocation/deallocation
functions.
However, it is surpisingly vague on requirements to the behaviour
of user-defined deallocation function and an interaction between
delete-expression and deallocation function.
This caused a heated argument on fido7.su.c-cpp newsgroup.</P>

<P>Resume:</P>

<P>It is not clear if user-supplied deallocation function is called from
delete-expr when the operand of delete-expr is the null
pointer (5.3.5&nbsp;



 <A HREF="expr.html#expr.delete">expr.delete</A>).
If it is, standard does not specify what user-supplied
deallocation function shall do with
the null pointer operand (18.4.1&nbsp;



 <A HREF="lib-support.html#lib.new.delete">lib.new.delete</A>).
Instead, Standard uses the term "has no effect", which meaning
is too vague in context given (5.3.5&nbsp;



 <A HREF="expr.html#expr.delete">expr.delete</A>).</P>

<P>Description:</P>

<P>Consider statements
<PRE>
   char* p= 0; //result of failed non-throwing ::new char[]
   ::delete[] p;
</PRE>
Argument passed to delete-expression is valid - it is the result
of a call to the non-throwing version of ::new, which has been failed.
5.3.5&nbsp;



 <A HREF="expr.html#expr.delete">expr.delete</A> paragraph 1 explicitly prohibit us to pass 0
without having the ::new failure.</P>

<P>Standard does NOT specify whether user-defined deallocation function
should be called in this case, or not.</P>

<P>Specifically, standard says in 5.3.5&nbsp;



 <A HREF="expr.html#expr.delete">expr.delete</A> paragraph 2:
<BLOCKQUOTE>
   ...if the value of the operand of delete is the null pointer the operation
   has no effect.
</BLOCKQUOTE>
Standard doesn't specify term "has no effect".
It is not clear from this context, whether the called deallocation function
is required to have no effect, or delete-expression shall not call
the deallocation function.</P>
<P>Furthermore, in para 4 standard says on default deallocation function:
<BLOCKQUOTE>
   If the delete-expression calls the implementation deallocation
   function (3.7.3.2&nbsp;



 <A HREF="basic.html#basic.stc.dynamic.deallocation">basic.stc.dynamic.deallocation</A>),
   if the operand of the delete expression is not
   the null pointer constant, ...
</BLOCKQUOTE>
Why it is so specific on interaction of default deallocation function
and delete-expr?</P>

<P>If "has no effect" is a requirement to the deallocation function,
then it should be stated in 3.7.3.2&nbsp;



 <A HREF="basic.html#basic.stc.dynamic.deallocation">basic.stc.dynamic.deallocation</A>,
or in 18.4.1.1&nbsp;



 <A HREF="lib-support.html#lib.new.delete.single">lib.new.delete.single</A> and
18.4.1.2&nbsp;



 <A HREF="lib-support.html#lib.new.delete.array">lib.new.delete.array</A>,
and it should be stated explicitly.</P>

<P>Furthermore, standard does NOT specify what actions shall
be performed by user-supplied deallocation function if NULL
is given (18.4.1.1&nbsp;



 <A HREF="lib-support.html#lib.new.delete.single">lib.new.delete.single</A> paragraph 12):</P>
<BLOCKQUOTE>
   Required behaviour: accept a value of ptr that is null or that was
   returned by an earlier call to the default
<TT>operator new(std::size_t)</TT>
   or <TT>operator new(std::size_t, const std::nothrow_t&amp;)</TT>.
</BLOCKQUOTE>

<P>The same corresponds to ::delete[] case.</P>

<P>Expected solution:</P>

<OL>
<LI>
Make it clear that delete-expr will not call deallocation function
if null pointer is given (in 5.3.5&nbsp;



 <A HREF="expr.html#expr.delete">expr.delete</A>).
</LI>
<LI>
Specify what user deallocation function shall do when null is given
(either in 3.7.3.2&nbsp;



 <A HREF="basic.html#basic.stc.dynamic.deallocation">basic.stc.dynamic.deallocation</A>, or
in 18.4.1.1&nbsp;



 <A HREF="lib-support.html#lib.new.delete.single">lib.new.delete.single</A>, and
18.4.1.2&nbsp;



 <A HREF="lib-support.html#lib.new.delete.array">lib.new.delete.array</A>).
</LI>
</OL>

<P>
<B>Notes from October 2002 meeting:</B>
</P>

<P>We believe that study of 18.4.1.1&nbsp;



 <A HREF="lib-support.html#lib.new.delete.single">lib.new.delete.single</A> paragraphs
12 and 13, 18.4.1.2&nbsp;



 <A HREF="lib-support.html#lib.new.delete.array">lib.new.delete.array</A> paragraphs 11 and 12, and
3.7.3.2&nbsp;



 <A HREF="basic.html#basic.stc.dynamic.deallocation">basic.stc.dynamic.deallocation</A> paragraph 3 shows that the
system-provided operator delete functions must accept a null pointer and
ignore it.  Those sections also show that a user-written replacement
for the system-provided operator delete functions must accept a
null pointer.  There is no requirement that such functions ignore
a null pointer, which is okay -- perhaps the reason for replacing the
system-provided functions is to do something special
with null pointer values (e.g., log such calls and return).</P>

<P>We believe that the standard should not require an implementation
to call a delete function with a null pointer, but it must allow
that.  For the system-provided delete functions or replacements
thereof, the standard already makes it clear that the delete
function must accept a null pointer.  For class-specific delete
functions, we believe the standard should require that such
functions accept a null pointer, though it should not mandate
what they do with null pointers.</P>

<P>5.3.5&nbsp;



 <A HREF="expr.html#expr.delete">expr.delete</A> needs to be updated to say that
it is unspecified whether or not the operator delete function is
called with a null pointer, and 3.7.3.2&nbsp;



 <A HREF="basic.html#basic.stc.dynamic.deallocation">basic.stc.dynamic.deallocation</A>
needs to be updated to say that any deallocation function must
accept a null pointer.</P>

<P>
<B>Proposed resolution (October, 2004):</B>
</P>

<OL>

<LI>
<P>Change 5.3.5&nbsp;



 <A HREF="expr.html#expr.delete">expr.delete</A> paragraph 2 as
indicated:</P>

<BLOCKQUOTE>

If the operand has a class type, the operand is converted to a
pointer type by calling the above-mentioned conversion function,
and the converted operand is used in place of the original
operand for the remainder of this section. In either alternative,
<S>if</S> the value of the operand of <TT>delete</TT> <S>is the
null pointer the operation has no effect</S> <B>may be a null
pointer value. If it is not a null pointer value, in</B>
<S>In</S> the first alternative (<I>delete object</I>), the value
of the operand of <TT>delete</TT> shall be a pointer to a
non-array object or a pointer to a sub-object (1.8&nbsp;



 <A HREF="intro.html#intro.object">intro.object</A>) representing a base class of such an object
(clause 10&nbsp;



 <A HREF="derived.html#class.derived">class.derived</A>)...

</BLOCKQUOTE>

</LI>

<LI>
<P>Change 5.3.5&nbsp;



 <A HREF="expr.html#expr.delete">expr.delete</A> paragraph 4 as
follows (note that the old wording reflects the changes proposed
by <A HREF="
     cwg_defects.html#442">issue 442</A>:</P>

<BLOCKQUOTE>

<P>The <I>cast-expression</I> in a <I>delete-expression</I> shall
be evaluated exactly once. <S>If the delete-expression calls the
implementation deallocation function (3.7.3.2&nbsp;



 <A HREF="basic.html#basic.stc.dynamic.deallocation">basic.stc.dynamic.deallocation</A>), and if the value of the operand of the
delete expression is not a null pointer, the deallocation
function will deallocate the storage referenced by the pointer
thus rendering the pointer invalid. [<I>Note:</I> the value of a
pointer that refers to deallocated storage is
indeterminate. &mdash;<I>end note</I>]</S>
</P>

</BLOCKQUOTE>

</LI>

<LI>
<P>Change 5.3.5&nbsp;



 <A HREF="expr.html#expr.delete">expr.delete</A> paragraphs 6-7 as
follows:</P>

<BLOCKQUOTE>

<P>
<S>The</S> <B>If the value of the operand of the
<I>delete-expression</I> is not a null pointer value, the</B>
<I>delete-expression</I> will invoke the destructor (if any) for
the object or the elements of the array being deleted. In the
case of an array, the elements will be destroyed in order of
decreasing address (that is, in reverse order of the completion
of their constructor; see 12.6.2&nbsp;



 <A HREF="special.html#class.base.init">class.base.init</A>).</P>

<P>
<S>The</S> <B>If the value of the operand of the <I>delete-expression</I> is not a
null pointer value, the</B> <I>delete-expression</I> will call a
deallocation function (3.7.3.2&nbsp;



 <A HREF="basic.html#basic.stc.dynamic.deallocation">basic.stc.dynamic.deallocation</A>). <B>Otherwise, it is unspecified
whether the deallocation function will be called.</B> [<I>Note:</I> The
deallocation function is called regardless of whether the
destructor for the object or some element of the array throws an
exception. &mdash;<I>end note</I>]</P>

</BLOCKQUOTE>

</LI>

<LI>
<P>Change 3.7.3.2&nbsp;



 <A HREF="basic.html#basic.stc.dynamic.deallocation">basic.stc.dynamic.deallocation</A> paragraph 3 as
indicated:</P>

<BLOCKQUOTE>

The value of the first argument supplied to <S>one of the</S> <B>a</B>
deallocation function<S>s provided in the standard library</S> may be a
null pointer value; if so, <B>and if the deallocation function is
one supplied in the standard library,</B> the call <S>to the
deallocation function</S> has no effect. Otherwise, the value
supplied to <TT>operator delete(void*)</TT> in the standard library shall
be one of the values returned by a previous invocation of either
<TT>operator new(std::size_t)</TT> or <TT>operator new(std::size_t, const
std::nothrow_t&amp;)</TT> in the standard library, and the value supplied
to <TT>operator delete[](void*)</TT> in the standard library shall be one
of the values returned by a previous invocation of either
<TT>operator new[](std::size_t)</TT> or <TT>operator new[](std::size_t, const
std::nothrow_t&amp;)</TT> in the standard library.

</BLOCKQUOTE>

</LI>

</OL>

<P>
<I>[Note: this resolution also resolves
<A HREF="
     cwg_defects.html#442">issue 442</A>.]</I>
</P>

<BR>
<BR>
<HR>
<A NAME="119"></A>
<H4>119.
  
Object lifetime and aggregate initialization
</H4>
<B>Section: </B>3.8&nbsp;



 <A HREF="basic.html#basic.life">basic.life</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Jack Rouse
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>20 May 1999<BR>



<P>[Moved to DR at 4/02 meeting.]</P>



<P>
<B>Jack Rouse:</B>
3.8&nbsp;



 <A HREF="basic.html#basic.life">basic.life</A>
 paragraph 1
includes:</P>
<BLOCKQUOTE>
The lifetime of an object is a runtime property of the object. The
lifetime of an object of type <TT>T</TT> begins when:
<UL>
<LI>storage with the proper alignment and size for type <TT>T</TT>
is obtained, and</LI>

<LI>if <TT>T</TT> is a class type with a non-trivial constructor
(12.1&nbsp;



 <A HREF="special.html#class.ctor">class.ctor</A>
), the
constructor call has completed.</LI>
</UL>
</BLOCKQUOTE>

Consider the code:
<PRE>
    struct B {
        B( int = 0 );
        ~B();
    };

    struct S {
        B b1;
    };

    int main()
    {
        S s = { 1 };
        return 0;
    }
</PRE>

In the code above, class <TT>S</TT> does have a non-trivial constructor, the
default constructor generated by the compiler.  According the text
above, the lifetime of the auto <TT>s</TT> would never begin because a
constructor for <TT>S</TT> is never called.  I think the second case in the
text needs to include aggregate initialization.

<P>
<B>Mike Miller:</B>
I see a couple of ways of fixing the problem.  One way would be
to change "the constructor call has completed" to "the object's
initialization is complete."</P>

<P>Another would be to add following "a class type with a non-trivial
constructor" the phrase "that is not initialized with the brace
notation (8.5.1&nbsp;



 <A HREF="decl.html#dcl.init.aggr">dcl.init.aggr</A>
)."</P>

<P>The first formulation treats aggregate initialization like a
constructor call; even POD-type members of an aggregate could
not be accessed before the aggregate initialization completed.
The second is less restrictive; the POD-type members of the
aggregate would be usable before the initialization, and the
members with non-trivial constructors (the only way an
aggregate can acquire a non-trivial constructor) would be
protected by recursive application of the lifetime rule.</P>

<P>
<B>Proposed resolution (04/01):</B> </P>

<P>In 3.8&nbsp;



 <A HREF="basic.html#basic.life">basic.life</A> paragraph 1, change</P>

<BLOCKQUOTE>

If <TT>T</TT> is a class type with a non-trivial constructor
(12.1&nbsp;



 <A HREF="special.html#class.ctor">class.ctor</A>), the constructor call has
completed.

</BLOCKQUOTE>

<P>to</P>

<BLOCKQUOTE>

If <TT>T</TT> is a class type with a non-trivial constructor
(12.1&nbsp;



 <A HREF="special.html#class.ctor">class.ctor</A>), the initialization is complete.
[<I>Note:</I> the initialization can be performed by a
constructor call or, in the case of an aggregate with an
implicitly-declared non-trivial default constructor, an
aggregate initialization (8.5.1&nbsp;



 <A HREF="decl.html#dcl.init.aggr">dcl.init.aggr</A>).]

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="274"></A>
<H4>274.
  
Cv-qualification and char-alias access to out-of-lifetime objects
</H4>
<B>Section: </B>3.8&nbsp;



 <A HREF="basic.html#basic.life">basic.life</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>14 Mar 2001<BR>


<P>[Voted into WP at April 2003 meeting.]</P>

<P>The wording in 3.8&nbsp;



 <A HREF="basic.html#basic.life">basic.life</A> paragraph 6 allows an
lvalue designating an out-of-lifetime object to be used as the
operand of a <TT>static_cast</TT> only if the conversion is
ultimately to "<TT>char&amp;</TT>" or "<TT>unsigned char&amp;</TT>".
This description excludes the possibility of using a cv-qualified
version of these types for no apparent reason.</P>

<P>
<B>Notes on 04/01 meeting:</B>
</P>

<P>The wording should be changed to allow cv-qualified char
types.</P>

<P>
<B>Proposed resolution (04/01):</B>
</P>

<P>In 3.8&nbsp;



 <A HREF="basic.html#basic.life">basic.life</A> paragraph 6 change the third bullet:
<UL>
<LI>
the lvalue is used as the operand of a <TT>static_cast</TT>
(5.2.9&nbsp;



 <A HREF="expr.html#expr.static.cast">expr.static.cast</A>)
(except when the conversion is ultimately to <TT>char&amp;</TT> or <TT>unsigned
char&amp;</TT>), or
</LI>
</UL>
to read:
<UL>
<LI>
the lvalue is used as the operand of a <TT>static_cast</TT>
(5.2.9&nbsp;



 <A HREF="expr.html#expr.static.cast">expr.static.cast</A>)
except when the conversion is ultimately to <TT><I>cv</I> char&amp;</TT> or
<TT><I>cv</I> unsigned char&amp;</TT>, or
</LI>
</UL>
</P>

<BR>
<BR>
<HR>
<A NAME="404"></A>
<H4>404.
  
Unclear reference to construction with non-trivial constructor
</H4>
<B>Section: </B>3.8&nbsp;



 <A HREF="basic.html#basic.life">basic.life</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>8 Apr 2003<BR>


<P>[Voted into WP at March 2004 meeting.]</P>

<P>3.8&nbsp;



 <A HREF="basic.html#basic.life">basic.life</A> paragraph 1 second bullet says:</P>
<BLOCKQUOTE>
if T is a class type with a non-trivial constructor (12.1),
the constructor call has completed.
</BLOCKQUOTE>

<P>This is confusing; what was intended is probably something like</P>
<BLOCKQUOTE>
if T is a class type and the constructor invoked to create the
object is non-trivial (12.1), the constructor call has completed.
</BLOCKQUOTE>

<P>
<B>Proposed Resolution (October 2003):</B>
</P>

<P>As given above.</P>

<BR>
<BR>
<HR>
<A NAME="158"></A>
<H4>158.
  
Aliasing and qualification conversions
</H4>
<B>Section: </B>3.10&nbsp;



 <A HREF="basic.html#basic.lval">basic.lval</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Stump
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>20 Aug 1999<BR>



<P>[Moved to DR at 4/02 meeting.]</P>

<P>3.10&nbsp;



 <A HREF="basic.html#basic.lval">basic.lval</A> paragraph 15 lists the types via which
an lvalue can be used to access the stored value of an object; using
an lvalue type that is not listed results in undefined behavior.  It
is permitted to add cv-qualification to the actual type of the object
in this access, but only at the top level of the type ("a cv-qualified
version of the dynamic type of the object").</P>

<P>However, 4.4&nbsp;



 <A HREF="conv.html#conv.qual">conv.qual</A> paragraph 4 permits a
"conversion [to] add cv-qualifiers at levels other than the first in
multi-level pointers."  The combination of these two rules
allows creation of pointers that cannot be dereferenced without
causing undefined behavior.  For instance:</P>

<PRE>
    int* jp;
    const int * const * p1 = &amp;jp;
    *p1;    // undefined behavior!
</PRE>

<P>The reason that <TT>*p1</TT> results in undefined behavior
is that the type of the lvalue is <TT>const int * const"</TT>,
which is <I>not</I> "a cv-qualified version of" <TT>int*</TT>.</P>

<P>Since the conversion is permitted, we must give it defined
semantics, hence we need to fix the wording in 3.10&nbsp;



 <A HREF="basic.html#basic.lval">basic.lval</A> to include all possible conversions of the type via
4.4&nbsp;



 <A HREF="conv.html#conv.qual">conv.qual</A>.</P>

<P>
<B>Proposed resolution (04/01):</B>
</P>

<P>Add a new bullet to 3.10&nbsp;



 <A HREF="basic.html#basic.lval">basic.lval</A> paragraph 15,
following "a cv-qualified version of the dynamic type of the
object:"</P>

<UL>
<LI>A type similar (as defined in 4.4&nbsp;



 <A HREF="conv.html#conv.qual">conv.qual</A>) to
the dynamic type of the object,</LI>
</UL>

<BR>
<BR>
<HR>
<A NAME="519"></A>
<H4>519.
  
Null pointer preservation in <TT>void*</TT> conversions
</H4>
<B>Section: </B>4.10&nbsp;



 <A HREF="conv.html#conv.ptr">conv.ptr</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>comp.std.c++
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>19 May 2005<BR>


<P>[Voted into WP at April, 2006 meeting.]</P>

<P>The C standard says in 6.3.2.3, paragraph 4:</P>

<BLOCKQUOTE>

Conversion of a null pointer to another pointer type yields a null
pointer of that type. Any two null pointers shall compare equal.

</BLOCKQUOTE>

<P>C++ appears to be incompatible with the first sentence in only two
areas:</P>

<PRE>
    A *a = 0;
    void *v = a;
</PRE>

<P>C++ (4.10&nbsp;



 <A HREF="conv.html#conv.ptr">conv.ptr</A> paragraph 2) says nothing about the
value of <TT>v</TT>.</P>

<PRE>
    void *v = 0;
    A *b = (A*)v; // aka static_cast&lt;A*&gt;(v)
</PRE>

<P>C++ (5.2.9&nbsp;



 <A HREF="expr.html#expr.static.cast">expr.static.cast</A> paragraph 10) says nothing about
the value of <TT>b</TT>.</P>

<P>
<U>Suggested changes</U>:</P>

<OL>

<LI>
<P>Add the following sentence to 4.10&nbsp;



 <A HREF="conv.html#conv.ptr">conv.ptr</A>
paragraph 2:</P>
</LI>

<BLOCKQUOTE>

The null pointer value is converted to the null pointer value of the
destination type.

</BLOCKQUOTE>

<LI>
<P>Add the following sentence to 5.2.9&nbsp;



 <A HREF="expr.html#expr.static.cast">expr.static.cast</A>
paragraph 10:</P>
</LI>

<BLOCKQUOTE>

The null pointer value (4.10&nbsp;



 <A HREF="conv.html#conv.ptr">conv.ptr</A>) is converted
to the null pointer value of the destination type.

</BLOCKQUOTE>

</OL>

<P>
<B>Proposed resolution (October, 2005):</B>
</P>

<OL>
<LI>
<P>Add the indicated words to 4.10&nbsp;



 <A HREF="conv.html#conv.ptr">conv.ptr</A>
paragraph 2:</P>
</LI>

<BLOCKQUOTE>

An rvalue of type &ldquo;pointer to <I>cv</I> <TT>T</TT>,&rdquo; where
<TT>T</TT> is an object type, can be converted to an rvalue of type &ldquo;pointer to
<I>cv</I> <TT>void</TT>&rdquo;. The result of converting a &ldquo;pointer to
<I>cv</I> <TT>T</TT>&rdquo; to a &ldquo;pointer
to <I>cv</I> <TT>void</TT>&rdquo; points to the start of the storage
location where the object of type <TT>T</TT> resides, as if the object
is a most derived object (1.8&nbsp;



 <A HREF="intro.html#intro.object">intro.object</A>) of
type <TT>T</TT> (that is, not a base class subobject). <B>The null
pointer value is converted to the null pointer value of the
destination type.</B>

</BLOCKQUOTE>

<LI>
<P>Add the indicated words to 5.2.9&nbsp;



 <A HREF="expr.html#expr.static.cast">expr.static.cast</A>
paragraph 11:</P>
</LI>

<BLOCKQUOTE>

An rvalue of type &ldquo;pointer to <I>cv1</I> <TT>void</TT>&rdquo;
can be converted to an rvalue of type &ldquo;pointer
to <I>cv2</I> <TT>T</TT>,&rdquo; where <TT>T</TT> is an object type
and <i>cv2</i> is the same cv-qualification as, or greater
cv-qualification than, <I>cv1</I>. <B>The null pointer value is
converted to the null pointer value of the destination type.</B> A
value of type pointer to object converted to &ldquo;pointer
to <I>cv</I> <TT>void</TT>&rdquo; and back, possibly with different
cv-qualification, shall have its original value...

</BLOCKQUOTE>

</OL>

<BR>
<BR>
<HR>
<A NAME="351"></A>
<H4>351.
  
Sequence point error: unspecified or undefined?
</H4>
<B>Section: </B>5&nbsp;



 <A HREF="expr.html#expr">expr</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Andrew Koenig
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>23 April 2002<BR>


<P>[Voted into WP at March 2004 meeting.]</P>



<P>I have found what looks like a bug in clause 5&nbsp;



 <A HREF="expr.html#expr">expr</A>,
paragraph 4:</P>
<BLOCKQUOTE>
   Between the previous and next sequence point a scalar object shall
   have its stored value modified at most once by the evaluation of an
   expression.  Furthermore, the prior value shall be accessed only to
   determine the value to be stored.  The requirements of this
   paragraph shall be met for each allowable ordering of the
   subexpressions of a full expression; otherwise the behavior is
   undefined.  Example:
<PRE>
        i = v[i++];                     // the behavior is unspecified
        i = 7, i++, i++;                // i becomes 9

        i = ++i + 1;                    // the behavior is unspecified
        i = i + 1;                      // the value of i is incremented
</PRE>
   --end example]
</BLOCKQUOTE>

<P>So which is it, unspecified or undefined?</P>

<P>
<B>Notes from October 2002 meeting:</B>
</P>

<P>We should find out what C99 says and do the same thing.</P>

<P>
<B>Proposed resolution (April 2003):</B>
</P>

<P>Change the example in clause 5&nbsp;



 <A HREF="expr.html#expr">expr</A>, paragraph 4 from</P>

<BLOCKQUOTE>
[<I>Example:</I>
<PRE>
i = v[i++];                     //<I>  the behavior is unspecified</I>
i = 7, i++, i++;                //<I>   </I>i<I>  becomes  </I>9

i = ++i + 1;                    //<I>  the behavior is unspecified</I>
i = i + 1;                      //<I>  the value of  </I>i<I>  is incremented</I>
</PRE>
--- end example]
</BLOCKQUOTE>

<P>to (changing "unspecified" to "undefined" twice)</P>

<BLOCKQUOTE>
[<I>Example:</I>
<PRE>
i = v[i++];                     //<I>  the behavior is undefined</I>
i = 7, i++, i++;                //<I>   </I>i<I>  becomes  </I>9

i = ++i + 1;                    //<I>  the behavior is undefined</I>
i = i + 1;                      //<I>  the value of  </I>i<I>  is incremented</I>
</PRE>
--- end example]
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="451"></A>
<H4>451.
  
Expressions with invalid results and ill-formedness
</H4>
<B>Section: </B>5&nbsp;



 <A HREF="expr.html#expr">expr</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Gennaro Prota
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>19 Jan 2004<BR>


<P>[Voted into WP at October 2005 meeting.]</P>

<P>Clause 5&nbsp;



 <A HREF="expr.html#expr">expr</A> par. 5 of the standard says:
<BLOCKQUOTE>
If during the evaluation
of an expression, the result is not mathematically defined or not in
the range of representable values for its type, the behavior is
undefined, unless such an expression is a constant expression (5.19),
in which case the program is ill-formed.
</BLOCKQUOTE>

<P>Well, we do know that except in some contexts (e.g. controlling
expression of a #if, array bounds), a compiler is not required to
evaluate constant-expressions in compile time, right?</P>

<P>Now, let us consider, the following simple snippet:</P>
<PRE>
  if (a &amp;&amp; 1/0)
      ...
</PRE>
with a, to fix our attention, being *not* a constant expression. The
quote above seems to say that since 1/0 is a constant
(sub-)expression, the program is ill-formed. So, is it the intent that
such ill-formedness is diagnosable at run-time? Or is it the intent
that the above gives undefined behavior (if 1/0 is evaluated) and is
not ill-formed?</P>

<P>I think the intent is actually the latter, so I propose the following
rewording of the quoted section:</P>
<BLOCKQUOTE>
  If an expression is evaluated but its result is not mathematically
   defined or not in the range of representable values
   for its type the behavior is undefined, unless such an expression
   is a constant expression (5.19) <B>that shall be evaluated during
   program translation</B>, in which case the program is ill-formed.
</BLOCKQUOTE>

<P>
<B>Rationale (March, 2004):</B>
</P>

<P>We feel the standard is clear enough.  The quoted sentence
does begin "If during the evaluation of an expression, ..."
so the rest of the sentence does not apply to an expression
that is not evaluated.</P>

<P>
<B>Note (September, 2004):</B>
</P>

<P>Gennaro Prota feels that the CWG missed the point of his
original comment: unless a constant expression appears in a
context that <I>requires</I> a constant expression, an
implementation is permitted to defer its evaluation to runtime.
An evaluation that fails at runtime cannot affect the
well-formedness of the program; only expressions that are
evaluated at compile time can make a program ill-formed.</P>

<P>The status has been reset to &ldquo;open&rdquo; to allow
further discussion.</P>

<P>
<B>Proposed resolution (October, 2004):</B>
</P>

<P>Change paragraph 5 of 5&nbsp;



 <A HREF="expr.html#expr">expr</A> as
indicated:</P>

<BLOCKQUOTE>

If during the evaluation of an expression, the result is not
mathematically defined or not in the range of representable
values for its type, the behavior is undefined, unless such an
expression <S>is a constant expression</S> <B>appears where an
integral constant expression is required</B> (5.19&nbsp;



 <A HREF="expr.html#expr.const">expr.const</A>), in which case the program is ill-formed.

</BLOCKQUOTE>
<BR>
<BR>
<HR>
<A NAME="122"></A>
<H4>122.
  
<I>template-id</I>s as <I>unqualified-id</I>s
</H4>
<B>Section: </B>5.1&nbsp;



 <A HREF="expr.html#expr.prim">expr.prim</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>3 June 1999<BR>



<P>[Moved to DR at 10/01 meeting.]</P>



<P>5.1&nbsp;



 <A HREF="expr.html#expr.prim">expr.prim</A>
 paragraph 11 reads,</P>

<BLOCKQUOTE>
A <I>template-id</I> shall be used as an <I>unqualified-id</I> only
as specified in
14.7.2&nbsp;



 <A HREF="template.html#temp.explicit">temp.explicit</A>
,
14.7&nbsp;



 <A HREF="template.html#temp.spec">temp.spec</A>
, and
14.5.4&nbsp;



 <A HREF="template.html#temp.class.spec">temp.class.spec</A>
.
</BLOCKQUOTE>

<P>What uses of <I>template-id</I>s
as <I>unqualified-id</I>s is this supposed to prevent?  And is the
list of referenced sections correct/complete?  For instance,
what about 14.8.1&nbsp;



 <A HREF="template.html#temp.arg.explicit">temp.arg.explicit</A>,
"Explicit template argument specification?"
Does its absence from the list in
5.1&nbsp;



 <A HREF="expr.html#expr.prim">expr.prim</A> paragraph 11 mean that
"<TT>f&lt;int&gt;()</TT>" is ill-formed?</P>

<P>This is even more confusing when you recall that <I>unqualified-id</I>s
are contained in <I>qualified-id</I>s:</P>

<BLOCKQUOTE>
    <I>qualified-id</I>:
        <TT>::</TT><SUB>opt</SUB>&nbsp;<I>nested-name-specifier</I>&nbsp;<TT>template</TT><SUB>opt</SUB>&nbsp;<I>unqualified-id</I>
</BLOCKQUOTE>

<P>Is the wording intending to say "used as an <I>unqualified-id</I>
that is not part of a <I>qualified-id</I>?"  Or something else?</P>

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>Remove the referenced sentence altogether.</P>

<BR>
<BR>
<HR>
<A NAME="125"></A>
<H4>125.
  
Ambiguity in <TT>friend</TT> declaration syntax
</H4>
<B>Section: </B>5.1&nbsp;



 <A HREF="expr.html#expr.prim">expr.prim</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Martin von Loewis
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>7 June 1999<BR>



<P>[Voted into WP at March 2004 meeting.]</P>

<P>The example below is ambiguous.</P>

<PRE>
    struct A{
      struct B{};
    };

    A::B C();

    namespace B{
      A C();
    }

    struct Test {
      friend A::B ::C();
    };
</PRE>

Here, it is not clear whether the friend declaration denotes
<TT>A B::C()</TT> or <TT>A::B C()</TT>, yet the standard does not resolve this
ambiguity.

<P>The ambiguity arises since both the <I>simple-type-specifier</I>
(7.1.5.2&nbsp;



 <A HREF="dcl.html#dcl.type.simple">dcl.type.simple</A>
 paragra 1) and an
<I>init-declararator</I>
(8&nbsp;



 <A HREF="decl.html#dcl.decl">dcl.decl</A>
 paragraph 1)
contain an optional <TT>::</TT> and an optional
<I>nested-name-specifier</I>
(5.1&nbsp;



 <A HREF="expr.html#expr.prim">expr.prim</A>
 paragraph 1).
Therefore, two different ways to analyse this code are
possible:</P>

<BLOCKQUOTE>
<I>simple-type-specifier</I> = <TT>A::B</TT>
<BR>
<I>init-declarator</I> = <TT>::C()</TT>
<BR>
<I>simple-declaration</I> = <TT>friend A::B ::C();</TT>
</BLOCKQUOTE>

or

<BLOCKQUOTE>
<I>simple-type-specifier</I> = <TT>A</TT>
<BR>
<I>init-declarator</I> = <TT>::B::C()</TT>
<BR>
<I>simple-declaration</I> = <TT>friend A ::B::C();</TT>
</BLOCKQUOTE>

Since it is a friend declaration, the init-declarator may be
qualified, and start with a global scope.

<P>Suggested Resolution: In the definition of
<I>nested-name-specifier</I>, add a
sentence saying that a <TT>::</TT> token immediately following a
<I>nested-name-specifier</I> is always considered as part of the
<I>nested-name-specifier</I>. Under this interpretation, the example is
ill-formed, and should be corrected as either</P>

<PRE>
    friend A (::B::C)();   //or
    friend A::B (::C)();
</PRE>

<P>An alternate suggestion &mdash; changing
7.1&nbsp;



 <A HREF="dcl.html#dcl.spec">dcl.spec</A>
 to say that</P>

<BLOCKQUOTE>
The longest sequence of <B>tokens</B> that could possibly be a type
name is taken as the <I>decl-specifier-seq</I> of a <I>declaration</I>.
</BLOCKQUOTE>

<P>&mdash; is undesirable because it would make the example well-formed
rather than requiring the user to disambiguate the declaration
explicitly.</P>

<P>
<B>Proposed resolution (04/01):</B>
</P>

<P>
<B>(See below for problem with this, from 10/01 meeting.)</B>
</P>

<P>In 5.1&nbsp;



 <A HREF="expr.html#expr.prim">expr.prim</A> paragraph 7,</P>

<OL>

<LI>
<P>Before the grammar for <I>qualified-id</I>, start a new
paragraph 7a with the text </P>

<BLOCKQUOTE>

A <I>qualified-id</I> is an <I>id-expression</I> that contains the
scope resolution operator <TT>::</TT>.

</BLOCKQUOTE>

</LI>

<LI>
<P>Following the grammar fragment, insert the following:</P>

<BLOCKQUOTE>

<P>The longest sequence of tokens that could form a <I>qualified-id</I>
constitutes a single <I>qualified-id</I>.  [<I>Example:</I>
</P>

<PRE>
    // classes C, D; functions F, G, namespace N; non-class type T
    friend C ::D::F();   // ill-formed, means friend (C::D::F)();
    friend C (::D::F)(); // well-formed
    friend N::T ::G();   // ill-formed, means friend (N::T::G)();
    friend N::T (::G)(); // well-formed
</PRE>

<P>&mdash;<I>end example</I>]</P>

</BLOCKQUOTE>

</LI>

<LI>
<P>Start a new paragraph 7b following the example.</P>
</LI>

</OL>

<P>(This resolution depends on that of
<A HREF="
     cwg_active.html#215">issue 215</A>.)</P>

<P>
<B>Notes from 10/01 meeting:</B>
</P>

<P>It was pointed out that the proposed resolution does not deal with
cases like <TT>X::Y</TT> where <TT>X</TT> is a type but not a class type.
The working group reaffirmed its decision that the disambiguation should
be syntactic only, i.e., it should depend only on whether or not the name is a
type.</P>

<U>Jason Merrill</U>
:

<P>At the Seattle meeting, I suggested that a solution might be to change the
<I>class-or-namespace-name</I> in the <I>nested-name-specifier</I>
rule to just be
"identifier"; there was some resistance to this idea.  FWIW, I've tried
this in g++.  I had to revise the idea so that only the second and
subsequent names were open to being any identifier, but that seems to work
just fine.</P>

<P>So, instead of</P>

<UL>
<I>nested-name-specifier</I>:
<UL>
<I>class-or-namespace-name</I> <TT>::</TT> <I>nested-name-specifier</I><SUB>opt</SUB>
<BR>
<I>class-or-namespace-name</I> <TT>::</TT> <I>template nested-name-specifier</I>
</UL>
</UL>

<P>it would be</P>

<UL>
<I>nested-name-specifier</I>:
<UL>
<I>type-or-namespace-name</I> <TT>::</TT> (per issue 215)
<BR>
<I>nested-name-specifier</I> <I>identifier</I> <TT>::</TT>
<BR>
<I>nested-name-specifier</I> <TT>template</TT> <I>template-id</I> <TT>::</TT>
</UL>
</UL>

<P>Or some equivalent but right-associative formulation, if people feel that's
important, but it seems irrelevant to me.</P>

<P>
<U>Clark Nelson</U>
:</P>

<P>Personally, I prefer the left-associative rule. I think it makes it easier
to understand. I was thinking about this production a lot at the meeting,
considering also some issues related to <A HREF="
     cwg_defects.html#301">301</A>.
My formulation was getting kind
of ugly, but with a left-associative rule, it gets a lot nicer.</P>

<P>Your proposal isn't complete, however, as it doesn't allow template
arguments without an explicit template keyword. You probably want to add an
alternative for:</P>

<UL>
<I>nested-name-specifier type-or-namespace-name</I> <TT>::</TT>
</UL>

<P>There is admittedly overlap between this alternative and</P>

<UL>
<I>nested-name-specifier identifier</I> <TT>::</TT>
</UL>

<P>but I think they're both necessary.</P>

<P>
<B>Notes from the 4/02 meeting:</B>
</P>

<P>The changes look good.  Clark Nelson will merge the two proposals
to produce a single proposed resolution.</P>

<P>
<B>Proposed resolution (April 2003):</B>
</P>

<P>
<I>nested-name-specifier</I> is currently defined in
5.1&nbsp;



 <A HREF="expr.html#expr.prim">expr.prim</A> paragraph 7 as:
</P>

<UL>
<I>nested-name-specifier:</I>
<UL>
<I>class-or-namespace-name</I> <TT>::</TT> <I>nested-name-specifier<sub>opt</sub></I>
<BR>
<I>class-or-namespace-name</I> <TT>:: template</TT> <I>nested-name-specifier</I>
</UL>
<I>class-or-namespace-name:</I>
<UL>
<I>class-name</I>
<BR>
<I>namespace-name</I>
</UL>
</UL>

<P>
The proposed definition is instead:
</P>

<UL>
<I>nested-name-specifier:</I>
<UL>
<I>type-name</I> <TT>::</TT>
<BR>
<I>namespace-name</I> <TT>::</TT>
<BR>
<I>nested-name-specifier</I> <I>identifier</I> <TT>::</TT>
<BR>
<I>nested-name-specifier</I> <TT>template</TT><I><sub>opt</sub> template-id</I> <TT>::</TT>
</UL>
</UL>
<P>
<A HREF="
     cwg_active.html#215">Issue 215</A>
is addressed by using <I>type-name</I> instead of <I>class-name</I> in the first alternative.
Issue 125 (this issue)
is addressed by using <I>identifier</I> instead of anything more specific in the third alternative.
Using left association instead of right association helps eliminate the need for <I>class-or-namespace-name</I> (or <I>type-or-namespace-name</I>, as suggested for <A HREF="
     cwg_active.html#215">issue 215</A>).
</P>

<P>
It should be noted that this formulation also rules out the possibility of <TT>A::template B::</TT>, i.e. using the <TT>template</TT> keyword without any template arguments.
I think this is according to the purpose of the <TT>template</TT> keyword, and that the former rule allowed such a construct only because of the difficulty of formulation of a right-associative rule that would disallow it.
But I wanted to be sure to point out this implication.
</P>

<P>
<B>Notes from April 2003 meeting:</B>
</P>

<P>See also <A HREF="
     cwg_active.html#96">issue 96</A>.</P>

<P>The proposed change resolves only part of
<A HREF="
     cwg_active.html#215">issue 215</A>.</P>

<BR>
<BR>
<HR>
<A NAME="113"></A>
<H4>113.
  
Visibility of called function
</H4>
<B>Section: </B>5.2.2&nbsp;



 <A HREF="expr.html#expr.call">expr.call</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Christophe de Dinechin
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>5 May 1999<BR>



<P>[Moved to DR at 10/01 meeting.]</P>



<P>
<B>Christophe de Dinechin:</B>
In 5.2.2&nbsp;



 <A HREF="expr.html#expr.call">expr.call</A>
, paragraph 2 reads:</P>

<BLOCKQUOTE>
If no declaration of the called function is visible from the scope  of
the call the program is ill-formed.
</BLOCKQUOTE>

I think nothing there or in the previous paragraph indicates that  
this does not apply to calls through pointer or virtual calls.

<P>
<B>Mike Miller:</B>
"The called function" is unfortunate phraseology; it makes it
sound as if it's referring to the function actually called, as
opposed to the identifier in the postfix expression.  It's
wrong with respect to Koenig lookup, too (the declaration need
not be visible if it can be found in a class or namespace
associated with one or more of the arguments).</P>

<P>In fact, this paragraph should be a note.  There's a general
rule that says you have to find an unambiguous declaration of
any name that is used
(3.4&nbsp;



 <A HREF="basic.html#basic.lookup">basic.lookup</A>
 paragraph 1);
the only reason this paragraph
is here is to contrast with C's implicit declaration of called
functions.</P>

<P>
<B>Proposed resolution:</B>
</P>
Change section 5.2.2&nbsp;



 <A HREF="expr.html#expr.call">expr.call</A> paragraph 2 from:
<BLOCKQUOTE>If no declaration of the called function is visible from the
scope of the call the program is ill-formed.</BLOCKQUOTE>
to:
<BLOCKQUOTE>[<I>Note:</I> if a function or member function name is used,
and name lookup (3.4&nbsp;



 <A HREF="basic.html#basic.lookup">basic.lookup</A>) does not find a
declaration of that name,
the program is ill-formed. No function is implicitly declared by such
a call. ]</BLOCKQUOTE>

<P>(See also <A HREF="
     cwg_active.html#218">issue 218</A>.)</P>

<BR>
<BR>
<HR>
<A NAME="466"></A>
<H4>466.
  
cv-qualifiers on pseudo-destructor type
</H4>
<B>Section: </B>5.2.4&nbsp;



 <A HREF="expr.html#expr.pseudo">expr.pseudo</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mark Mitchell
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>18 Mar 2004<BR>


<P>[Voted into WP at April, 2006 meeting.]</P>

<P>5.2.4&nbsp;



 <A HREF="expr.html#expr.pseudo">expr.pseudo</A> paragraph 2 says both:
<BLOCKQUOTE>
  The type designated by the pseudo-destructor-name shall be the same
  as the object type.
</BLOCKQUOTE>
and also:
<BLOCKQUOTE>
  The cv-unqualified versions of the object type and of the type
  designated by the pseudo-destructor-name shall be the same type.
</BLOCKQUOTE>
Which is it?  "The same" or "the same up to cv-qualifiers"?  The
second sentence is more generous than the first.  Most compilers seem
to implement the less restrictive form, so I guess that's what I think
we should do.</P>

<P>See also issues <A HREF="
     cwg_defects.html#305">305</A> and
<A HREF="
     cwg_active.html#399">399</A>.</P>

<P>
<B>Proposed resolution (October, 2005):</B>
</P>

<P>Change 5.2.4&nbsp;



 <A HREF="expr.html#expr.pseudo">expr.pseudo</A> paragraph 2 as follows:</P>

<BLOCKQUOTE>

The left-hand side of the dot operator shall be of scalar type. The
left-hand side of the arrow operator shall be of pointer to scalar
type. This scalar type is the object type. <S>The type designated by the
<I>pseudo-destructor-name</I> shall be the same as the object
type.</S> <B>The cv-unqualified versions of
the object type and of the type designated by the
<I>pseudo-destructor-name</I> shall be the same type.</B> Furthermore,
the two <I>type-name</I>s in a <I>pseudo-destructor-name</I> of the
form

<UL>
<TT>::</TT><I><SUB>opt</SUB> nested-name-specifier<SUB>opt</SUB> type-name </I><TT>::~</TT><I> type-name</I>
</UL>

shall designate the same scalar type. <S>The cv-unqualified versions of
the object type and of the type designated by the
<I>pseudo-destructor-name</I> shall be the same type.</S>

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="421"></A>
<H4>421.
  
Is rvalue.field an rvalue?
</H4>
<B>Section: </B>5.2.5&nbsp;



 <A HREF="expr.html#expr.ref">expr.ref</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Gabriel Dos Reis
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>15 June 2003<BR>


<P>[Voted into WP at March 2004 meeting.]</P>



<P>Consider</P>
<PRE>
  typedef
    struct {
      int a;
    } A;

  A f(void)
  {
    A a;
    return a;
  }

  int main(void)
  {
    int* p = &amp;f().a;   // #1
  }
</PRE>
<P>Should #1 be rejected?  The standard is currently silent.</P>

<P>
<U>Mike Miller:</U>
I don't believe the Standard is silent on this.  I will agree that the
wording of 5.2.5&nbsp;



 <A HREF="expr.html#expr.ref">expr.ref</A> paragraph 4 bullet 2 is
unfortunate, as it is subject to misinterpretation.  It reads,
<BLOCKQUOTE>
    If E1 is an lvalue, then E1.E2 is an lvalue.
</BLOCKQUOTE>
The intent is, "and not otherwise." </P>

<P>
<B>Notes from October 2003 meeting:</B>
</P>

<P>We agree the reference should be an rvalue, and a change along
the lines of that recommended by Mike Miller is reasonable.</P>

<P>
<B>Proposed Resolution (October 2003):</B>
</P>

<P>Change the second bullet of 5.2.5&nbsp;



 <A HREF="expr.html#expr.ref">expr.ref</A>
paragraph 4 to read: </P>
<BLOCKQUOTE>
If E1 is an lvalue, then E1.E2 is an lvalue<B>; otherwise, it is an rvalue</B>.
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="492"></A>
<H4>492.
  
<TT>typeid</TT> constness inconsistent with example
</H4>
<B>Section: </B>5.2.8&nbsp;



 <A HREF="expr.html#expr.typeid">expr.typeid</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Ron Natalie
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>15 Dec 2004<BR>


<P>[Voted into WP at April, 2006 meeting.]</P>

<P>There is an inconsistency between the normative text in
section 5.2.8&nbsp;



 <A HREF="expr.html#expr.typeid">expr.typeid</A> and
the example that follows.</P>

<P>Here is the relevant passage (starting with paragraph 4):</P>

<BLOCKQUOTE>

<P>
When <TT>typeid</TT> is applied to a <I>type-id</I>, the result
refers to a <TT>std::type_info</TT> object representing the type of the
<I>type-id</I>. If the type of the <I>type-id</I> is a reference
type, the result of the <TT>typeid</TT> expression refers to a
<TT>std::type_info</TT> object representing the referenced type.
</P>

<P>
The top-level cv-qualifiers of the lvalue expression or the
<I>type-id</I> that is the operand of <TT>typeid</TT> are always
ignored.
</P>

</BLOCKQUOTE>

<P>and the example:</P>

<PRE>
    typeid(D) == typeid(const D&amp;); // yields true
</PRE>

<P>
The second paragraph above says the &ldquo;<I>type-id</I> that is
the operand&rdquo;.  This would be <TT>const D&amp;</TT>.  In
this case, the <TT>const</TT> is not at the top-level (i.e.,
applied to the operand itself).
</P>

<P>By a strict reading, the above should yield <TT>false</TT>.</P>

<P>
My proposal is that the strict reading of the normative test is correct.
The example is wrong.   Different compilers here give different
answers.
</P>

<P>
<B>Proposed resolution (April, 2005):</B>
</P>

<P>Change the second sentence of 5.2.8&nbsp;



 <A HREF="expr.html#expr.typeid">expr.typeid</A>
paragraph 4 as follows:</P>

<BLOCKQUOTE>

If the type of the <I>type-id</I> is a reference <B>to a possibly
cv-qualified</B> type, the result of the <TT>typeid</TT> expression
refers to a <TT>std::type_info</TT> object representing the
<B>cv-unqualified</B> referenced type.

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="54"></A>
<H4>54.
  
Static_cast from private base to derived class
</H4>
<B>Section: </B>5.2.9&nbsp;



 <A HREF="expr.html#expr.static.cast">expr.static.cast</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Adamczyk
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>13 Oct 1998<BR>



<P>[Voted into WP at October 2004 meeting.]</P>

<P>Is it okay to use a <TT>static_cast</TT> to cast from a private base
class to a derived class? That depends on what the words "valid standard
conversion" in paragraph 8 mean &mdash; do they mean the conversion exists,
or that it would not get an error if it were done? I think the former
was intended &mdash; and therefore a <TT>static_cast</TT> from a private base
to a derived class would be allowed.</P>

<P>
<B>Rationale (04/99):</B> A <TT>static_cast</TT> from a private
base to a derived class is not allowed outside a member from the
derived class, because 4.10&nbsp;



 <A HREF="conv.html#conv.ptr">conv.ptr</A>

paragraph 3 implies that the conversion is not valid. (Classic style
casts work.)</P>

<P>
<B>Reopened September 2003:</B>
</P>

<P>
<U>Steve Adamczyk:</U>
It makes some sense to disallow the inverse conversion that is
pointer-to-member of derived to pointer-to-member of private base.
There's less justification for the pointer-to-private-base to
pointer-to-derived case.  EDG, g++ 3.2, and MSVC++ 7.1 allow
the pointer case and disallow the pointer-to-member case.
Sun disallows the pointer case as well.</P>

<PRE>
  struct B {};
  struct D : private B {};
  int main() {
    B *p = 0;
    static_cast&lt;D *&gt;(p);  // Pointer case: should be allowed
    int D::*pm = 0;
    static_cast&lt;int B::*&gt;(pm);  // Pointer-to-member case: should get error
  }
</PRE>

<P>There's a tricky case with old-style casts: because the
static_cast interpretation is tried first, you want a case
like the above to be considered a static_cast, but then issue
an error, not be rejected as not a static cast; if you did the
latter, you would then try the cast as a reinterpret_cast.</P>

<P>Ambiguity and casting to a virtual base should likewise be
errors after the static_cast interpretation is selected.</P>

<P>
<B>Notes from the October 2003 meeting:</B>
</P>

<P>There was lots of sentiment for making things symmetrical:
the pointer case should be the same as the pointer-to-member case.
g++ 3.3 now issues errors on both cases.</P>

<P>We decided an error should be issued on both cases.
The access part of the check should be done later; by some
definition of the word the static_cast is valid, and then
later an access error is issued.
This is similar to the way standard conversions work.</P>

<P>
<B>Proposed Resolution (October 2003):</B>
</P>

<P>Replace paragraph 5.2.9&nbsp;



 <A HREF="expr.html#expr.static.cast">expr.static.cast</A>/6:</P>

<BLOCKQUOTE>
The inverse of any standard conversion sequence (clause
4&nbsp;



 <A HREF="conv.html#conv">conv</A>), other than the
lvalue-to-rvalue (4.1&nbsp;



 <A HREF="conv.html#conv.lval">conv.lval</A>),
array-to-pointer (4.2&nbsp;



 <A HREF="conv.html#conv.array">conv.array</A>),
function-to-pointer (4.3&nbsp;



 <A HREF="conv.html#conv.func">conv.func</A>), and
boolean (4.12&nbsp;



 <A HREF="conv.html#conv.bool">conv.bool</A>) conversions, can be performed
explicitly using <TT>static_cast</TT>.
The lvalue-to-rvalue (4.1&nbsp;



 <A HREF="conv.html#conv.lval">conv.lval</A>),
array-to-pointer (4.2&nbsp;



 <A HREF="conv.html#conv.array">conv.array</A>), and
function-to-pointer (4.3&nbsp;



 <A HREF="conv.html#conv.func">conv.func</A>)
conversions are applied to the operand.
Such a
<TT>static_cast</TT>
is subject to the restriction that the explicit conversion does not
cast away constness (5.2.11&nbsp;



 <A HREF="expr.html#expr.const.cast">expr.const.cast</A>), and the following
additional rules for specific cases:
</BLOCKQUOTE>

<P>with two paragraphs:</P>

<BLOCKQUOTE>
The inverse of any standard conversion sequence (clause
4&nbsp;



 <A HREF="conv.html#conv">conv</A>), other than the
lvalue-to-rvalue (4.1&nbsp;



 <A HREF="conv.html#conv.lval">conv.lval</A>),
array-to-pointer (4.2&nbsp;



 <A HREF="conv.html#conv.array">conv.array</A>),
function-to-pointer (4.3&nbsp;



 <A HREF="conv.html#conv.func">conv.func</A>), and
boolean (4.12&nbsp;



 <A HREF="conv.html#conv.bool">conv.bool</A>) conversions, can be performed
explicitly using <TT>static_cast</TT>.
<B>A program is ill-formed if it
uses <TT>static_cast</TT> to perform the inverse of an ill-formed
standard conversion sequence.[<I>Example:</I> 

<BLOCKQUOTE>
<PRE>
struct B {};
struct D : private B {};
void f() {
  static_cast&lt;D*&gt;((B*)0); // Error: B is a private base of D.
  static_cast&lt;int B::*&gt;((int D::*)0); // Error: B is a private base of D.
}
</PRE>
</BLOCKQUOTE>
--- end example]
</B>

<P>
The lvalue-to-rvalue (4.1&nbsp;



 <A HREF="conv.html#conv.lval">conv.lval</A>),
array-to-pointer (4.2&nbsp;



 <A HREF="conv.html#conv.array">conv.array</A>), and
function-to-pointer (4.3&nbsp;



 <A HREF="conv.html#conv.func">conv.func</A>)
conversions are applied to the operand.
Such a
<TT>static_cast</TT>
is subject to the restriction that the explicit conversion does not
cast away constness (5.2.11&nbsp;



 <A HREF="expr.html#expr.const.cast">expr.const.cast</A>), and the following
additional rules for specific cases:
</P>
</BLOCKQUOTE>

<P>In addition, modify the second sentence of
5.4&nbsp;



 <A HREF="expr.html#expr.cast">expr.cast</A>/5.  The first two
sentences of 5.4&nbsp;



 <A HREF="expr.html#expr.cast">expr.cast</A>/5 presently read:</P>

<BLOCKQUOTE>
The conversions performed by
<UL>
<LI>
a <TT>const_cast</TT> (5.2.11),
</LI>
<LI>
a <TT>static_cast</TT> (5.2.9),
</LI>
<LI>
a <TT>static_cast</TT> followed by a <TT>const_cast</TT>,
</LI>
<LI>
a <TT>reinterpret_cast</TT> (5.2.10), or
</LI>
<LI>
a <TT>reinterpret_cast</TT> followed by a <TT>const_cast</TT>,
</LI>
</UL>
can be performed using the cast notation of explicit type conversion.
The same semantic restrictions and behaviors apply.
</BLOCKQUOTE>

<P>Change the second sentence to read:</P>

<BLOCKQUOTE>
The same semantic restrictions and behaviors apply<B>, with the exception
that in performing a <TT>static_cast</TT> in the following situations
the conversion is valid even if the base class is inaccessible:

<UL>
<LI>a pointer to an object of derived class type or an lvalue of
derived class type may be explicitly converted to a pointer or
reference to an unambiguous base class type, respectively; </LI>

<LI>a pointer to member of derived class type may be explicitly
converted to a pointer to member of an unambiguous non-virtual base
class type; </LI>

<LI>a pointer to an object of an unambiguous non-virtual
base class type, an lvalue of an unambiguous non-virtual base
class type, or a pointer to member of an unambiguous
non-virtual base class type may be explicitly converted to a pointer,
a reference, or a pointer to member of a derived class type,
respectively.</LI>
</UL>
</B>
</BLOCKQUOTE>

<P>Remove paragraph 5.4&nbsp;



 <A HREF="expr.html#expr.cast">expr.cast</A>/7, which presently reads:</P>

<BLOCKQUOTE>
In addition to
those conversions,
the following
<TT>static_cast</TT>
and
<TT>reinterpret_cast</TT>
operations
(optionally followed by a
<TT>const_cast</TT>
operation)
may be performed using the cast notation of explicit type conversion,
even if the base class type is not accessible:
<UL>
<LI>
a pointer to an object of derived class type or an lvalue of derived class
type may be explicitly converted
to a pointer or reference to an unambiguous base class type, respectively;
</LI>
<LI>
a pointer to member of derived class type may be explicitly converted
to a pointer to member of an unambiguous non-virtual base class type;
</LI>
<LI>
a pointer to an object of non-virtual base class type, an lvalue
of non-virtual base class type, or a pointer to member of non-virtual
base class type may be explicitly converted to a pointer, a reference,
or a pointer to member of a derived class type, respectively.
</LI>
</UL>
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="427"></A>
<H4>427.
  
<TT>static_cast</TT> ambiguity: conversion versus cast to derived
</H4>
<B>Section: </B>5.2.9&nbsp;



 <A HREF="expr.html#expr.static.cast">expr.static.cast</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mark Mitchell
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>5 July 2003<BR>


<P>[Voted into WP at October 2004 meeting.]</P>

<P>Consider this code:</P>
<PRE>
  struct B {};

  struct D : public B { 
    D(const B&amp;);
  };

  extern B&amp; b;

  void f() {
    static_cast&lt;const D&amp;&gt;(b);
  }
</PRE>
<P>The rules for <TT>static_cast</TT> permit the conversion to
"const D&amp;" in two ways: </P>
<OL>
<LI>
D is derived from B, and b is an lvalue, so a cast to D&amp; is OK.
</LI>
<LI>
const D&amp; t = b is valid, using the constructor for D. [Ed. note:
actually, this should be parenthesized initialization.]
</LI>
</OL>
<P>The first alternative is 5.2.9&nbsp;



 <A HREF="expr.html#expr.static.cast">expr.static.cast</A>/5; the second is
5.2.9&nbsp;



 <A HREF="expr.html#expr.static.cast">expr.static.cast</A>/2.</P>

<P>Presumably the first alternative is better -- it's the "simpler"
conversion.  The standard does not seem to make that clear.</P>

<P>
<U>Steve Adamczyk:</U>
I take the "Otherwise" at the beginning of
5.2.9&nbsp;



 <A HREF="expr.html#expr.static.cast">expr.static.cast</A>/3 as meaning that
the paragraph 2 interpretation is used if available, which means in
your example above interpretation 2 would be used.  However, that's
not what EDG's compiler does, and I agree that it's not the "simpler"
conversion.</P>

<P>
<B>Proposed Resolution (October 2003):</B>
</P>

<P>Move paragraph 5.2.9/5:</P>

<BLOCKQUOTE>
<P>
An lvalue of type
``<I>cv1</I>
<TT>B</TT>'',
where
<TT>B</TT>
is a class type, can be cast to type ``reference to
<I>cv2</I>
<TT>D</TT>'',
where
<TT>D</TT>
is a class derived (clause
10&nbsp;



 <A HREF="derived.html#class.derived">class.derived</A>) from
<TT>B</TT>,
if a valid standard conversion from ``pointer to
<TT>D</TT>''
to ``pointer to
<TT>B</TT>''
exists (4.10&nbsp;



 <A HREF="conv.html#conv.ptr">conv.ptr</A>),
<I>cv2</I>
is the same cv-qualification as, or greater cv-qualification than,
<I>cv1</I>,
and
<TT>B</TT>
is not a virtual base class of
<TT>D</TT>.
The result is an lvalue of type
``<I>cv2</I> <TT>D</TT>.''
If the lvalue of type
``<I>cv1</I>
<TT>B</TT>''
is actually a sub-object of an object of type
<TT>D</TT>,
the lvalue refers to the enclosing object of type
<TT>D</TT>.
Otherwise, the result of the cast is undefined.
[<I>Example:</I>
<PRE>
  struct B {};
  struct D : public B {};
  D d;
  B &amp;br = d;

  static_cast&lt;D&amp;&gt;(br);            //<I>  produces lvalue to the original  </I>d<I>  object</I>
</PRE>
--- end example]
</P>
</BLOCKQUOTE>

<P>before paragraph 5.2.9&nbsp;



 <A HREF="expr.html#expr.static.cast">expr.static.cast</A>/2.</P>

<P>Insert <B>Otherwise,</B> before the text of paragraph
5.2.9&nbsp;



 <A HREF="expr.html#expr.static.cast">expr.static.cast</A>/2
(which will become 5.2.9&nbsp;



 <A HREF="expr.html#expr.static.cast">expr.static.cast</A>/3
after the above insertion), so that it
reads:</P>
<BLOCKQUOTE>
<P>
<b>Otherwise</b>, an expression
<TT>e</TT>
can be explicitly converted to a type
<TT>T</TT>
using a
<TT>static_cast</TT>
of the form
<TT>static_cast&lt;T&gt;(e)</TT>
if the declaration
<TT>"T t(e);"</TT>
is well-formed, for some invented temporary variable
<TT>t</TT>
(8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A>).
The effect of such an explicit conversion is the same as performing the
declaration and initialization and then using the temporary variable
as the result of the conversion.
The result is an lvalue if
<TT>T</TT>
is a reference type (8.3.2&nbsp;



 <A HREF="decl.html#dcl.ref">dcl.ref</A>), and an rvalue otherwise.
The expression
<TT>e</TT>
is used as an lvalue if and only if the initialization uses it as an lvalue.
</P>
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="439"></A>
<H4>439.
  
Guarantees on casting pointer back to cv-qualified version of original type
</H4>
<B>Section: </B>5.2.9&nbsp;



 <A HREF="expr.html#expr.static.cast">expr.static.cast</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mark Mitchell
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>30 Oct 2003<BR>


<P>[Voted into WP at April 2005 meeting.]</P>

<P>Paragraph 5.2.9&nbsp;



 <A HREF="expr.html#expr.static.cast">expr.static.cast</A> paragraph 10 says that:</P>

<BLOCKQUOTE>
A value of type pointer to object converted to
"pointer to <I>cv</I> <TT>void</TT>" and back to the
original pointer type will have its original value.
</BLOCKQUOTE>

<P>That guarantee should be stronger.  In particular, given:
<PRE>
  T* p1 = new T;
  const T* p2 = static_cast&lt;const T*&gt;(static_cast&lt;void *&gt;(p1));
  if (p1 != p2)
    abort ();
</PRE>
there should be no call to "abort".  The last sentence of Paragraph
5.2.9&nbsp;



 <A HREF="expr.html#expr.static.cast">expr.static.cast</A> paragraph 10 should be changed to read:</P>

<BLOCKQUOTE>
 A value of type pointer to object converted to "pointer to
<I>cv</I> <TT>void</TT>" and back to the original pointer type
(or a variant of the original pointer type that differs only in the
<I>cv</I>-qualifiers applied to the object type) will have its
original value.
[<I>Example:</I>
<BLOCKQUOTE>
<PRE>
T* p1 = new T;
const T* p2 = static_cast&lt;const T*&gt;(static_cast&lt;void *&gt;(p1));
bool b = p1 == p2; // b <I>will have the value true.</I>
</PRE>
</BLOCKQUOTE>
<I>---end example.</I>]
</BLOCKQUOTE>

<P>
<B>Proposed resolution:</B>
</P>

<P>Change 5.2.9&nbsp;



 <A HREF="expr.html#expr.static.cast">expr.static.cast</A> paragraph 10 as indicated:</P>
<BLOCKQUOTE>
A value of type pointer to object converted to "pointer to
<I>cv</I> <TT>void</TT>" and back to the original pointer
type<B>, possibly with different cv-qualification,</B> will have
its original value.  <B>[<I>Example:</I></B>
<PRE>
<B>
  T* p1 = new T;
  const T* p2 = static_cast&lt;const T*&gt;(static_cast&lt;void *&gt;(p1));
  bool b = p1 == p2; // b<I> will have the value </I>true.
</B>
</PRE>
<B>---<I>end example</I>]</B>
</BLOCKQUOTE>

<P>
<B>Rationale:</B> The wording "possibly with different
cv-qualification" was chosen over the suggested wording to
allow for changes in cv-qualification at different levels in a
multi-level pointer, rather than only at the object type level.
</P>

<BR>
<BR>
<HR>
<A NAME="195"></A>
<H4>195.
  
Converting between function and object pointers
</H4>
<B>Section: </B>5.2.10&nbsp;



 <A HREF="expr.html#expr.reinterpret.cast">expr.reinterpret.cast</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Clamage
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>12 Jan 2000<BR>



<P>[Voted into WP at April 2005 meeting.]</P>



<P>It is currently not permitted to cast directly between a pointer to
function type and a pointer to object type.  This conversion is not
listed in 5.2.9&nbsp;



 <A HREF="expr.html#expr.static.cast">expr.static.cast</A>
 and
5.2.10&nbsp;



 <A HREF="expr.html#expr.reinterpret.cast">expr.reinterpret.cast</A>
 and thus
requires a diagnostic to be issued.  However, if a sufficiently long
integral type exists (as is the case in many implementations), it is
permitted to cast between pointer to function types and pointer to
object types using that integral type as an intermediary.</P>

<P>In C the cast results in undefined behavior and thus does not
require a diagnostic, and Unix C compilers generally do not issue
one.  This fact is used in the definition of the standard Unix
function <TT>dlsym</TT>, which is declared to return <TT>void*</TT>
but in fact may return either a pointer to a function or a pointer to
an object.  The fact that C++ compilers are required to issue a
diagnostic is viewed as a "competitive disadvantage" for the language.</P>

<P>
<B>Suggested resolution:</B> Add wording to
5.2.10&nbsp;



 <A HREF="expr.html#expr.reinterpret.cast">expr.reinterpret.cast</A>
 allowing
conversions between pointer to function and pointer to object types,
if the implementation has an integral data type that can be used as an
intermediary.</P>

<P>Several points were raised in opposition to this suggestion:</P>

<BR>
<OL>
<LI>Early C++ supported this conversion and it was deliberately
removed during the standardization process.</LI>

<LI>The existence of an appropriate integral type is irrelevant to
whether the conversion is "safe."  The condition should be on whether
information is lost in the conversion or not.</LI>

<LI>There are numerous ways to address the problem at an
implementation level rather than changing the language.  For example,
the compiler could recognize the specific case of <TT>dlsym</TT> and
omit the diagnostic, or the C++ binding to <TT>dlsym</TT> could be
changed (using templates, for instance) to circumvent the violation.</LI>

<LI>The conversion is, in fact, not supported by C; the <TT>dlsym</TT>
function is simply relying on non-mandated characteristics of C
implementations, and we would be going beyond the requirements of C
compatibility in requiring (some) implementations to support the
conversion.</LI>

<LI>This issue is in fact not a defect (omitted or self-contradictory
requirements) in the current Standard; the proposed change would
actually be an extension and should not be considered until the full
review of the IS.</LI>

<LI>
<TT>dlsym</TT> appears not to be used very widely, and the
declaration in the header file is not problematic, only calls to it.
Since C code generally requires some porting to be valid C++ anyway,
this should be considered one of those items that requires porting.</LI>

</OL>

<P>Martin O'Riordan suggested an alternative approach:</P>

<BR>
<UL>
<LI>Do not allow the conversions to be performed via old-style casts.</LI>

<LI>Allow <TT>reinterpret_cast</TT> to perform the conversions with
the C-style semantics (undefined behavior if not supported).</LI>

<LI>Allow <TT>dynamic_cast</TT> to perform the conversions with
well-defined behavior: the result would be a null pointer if the
implementation could not support the requested conversion.</LI>
</UL>

<P>The advantage of this approach is that it would permit writing
portable, well-defined programs involving such conversions.  However,
it breaks the current degree of compatibility between old and new
casts, and it adds functionality to <TT>dynamic_cast</TT> which is not
obviously related to its current meaning.</P>

<P>
<U>Notes from 04/00 meeting:</U>
</P>

<P>Andrew Koenig suggested yet another approach: specify that "no
diagnostic is required" if the implementation supports the conversion.</P>

<P>
<B>Later note:</B>
</P>

<P>It was observed that conversion between function and data pointers
is listed as a "common extension" in C99.  </P>

<P>
<B>Notes on the 10/01 meeting:</B>
</P>

<P>It was decided that we want the conversion defined in such a way that
it always exists but is always undefined (as opposed to existing only
when the size relationship is appropriate, and being implementation-defined
in that case).  This would allow an implementation to issue an error
at compile time if the conversion does not make sense.</P>

<P>Bill Gibbons notes that the definitions of the other similar casts are
inconsistent in this regard.  Perhaps they should be updated as well.</P>

<P>
<B>Proposed resolution (April 2003):</B>
</P>

<P>After 5.2.10&nbsp;



 <A HREF="expr.html#expr.reinterpret.cast">expr.reinterpret.cast</A>
paragraph 6, insert:</P>
<BLOCKQUOTE>
A pointer to a 
function can be explicitly converted to a pointer to a function of a different 
type. The effect of calling a function through a pointer to a function
type (8.3.5&nbsp;



 <A HREF="decl.html#dcl.fct">dcl.fct</A>) 
that is not the same as the type used in the definition of the function is 
undefined. Except that converting an rvalue of type ``pointer to <TT>T1</TT>'' 
to the type ``pointer to <TT>T2</TT>'' (where <TT>T1</TT> and <TT>T2</TT> are 
function types) and back to its original type yields the original pointer 
value, the result of such a pointer conversion is unspecified. [Note: see
also 4.10&nbsp;



 <A HREF="conv.html#conv.ptr">conv.ptr</A> for more details of pointer conversions. ]
<B>It is implementation defined whether a conversion from pointer to object to 
pointer to function and/or a conversion from pointer to function to pointer to 
object exist. </B>
</BLOCKQUOTE>
and in paragraph 10:
<BLOCKQUOTE>
An lvalue expression of type <TT>T1</TT> can be cast to the type
``reference to <TT>T2</TT>'' 
if <B><TT>T1</TT> and <TT>T2</TT> are object types and</B> an expression of 
type ``pointer to <TT>T1</TT>'' can be explicitly converted to the type 
``pointer to <TT>T2</TT>'' using a reinterpret_cast. That is, a reference
cast <TT>reinterpret_cast&lt; T&amp; &gt;(x)</TT> has the same effect
as the conversion <TT>*reinterpret_cast&lt; T* &gt;(&amp;x)</TT> with
the built-in <TT>&amp;</TT> and <TT>*</TT> operators. 
The result is an lvalue that refers to the same object as the source lvalue, 
but with a different type. No temporary is created, no copy is made, and 
constructors (12.1&nbsp;



 <A HREF="special.html#class.ctor">class.ctor</A>) or conversion functions
(12.3&nbsp;



 <A HREF="special.html#class.conv">class.conv</A>) are not called.
</BLOCKQUOTE>
<P>
<I>Drafting Note:</I>
</P>
<P>If either conversion exists, the implementation already has to define the 
behavior (paragraph 3).</P>

<P>
<B>Notes from April 2003 meeting:</B>
</P>

<P>The new consensus is that if the implementation allows
this cast, pointer-to-function converted to pointer-to-object converted
back to the original pointer-to-function should work; anything else
is undefined behavior.  If the implementation does not allow the cast,
it should be ill-formed.</P>

<P>Tom Plum is investigating a new concept, that of a
"conditionally-defined" feature, which may be applicable here.</P>

<P>
<B>Proposed Resolution (October, 2004):</B>
</P>

<P>(See paper J16/04-0067 = WG21 N1627 for background material and
rationale for this resolution.  The resolution proposed here differs
only editorially from the one in the paper.)</P>

<OL>

<LI>
<P>Insert the following as 1.3.2 and renumber all following
definitions accordingly:</P>

<BLOCKQUOTE>
<P>
<B>1.3.2&nbsp;&nbsp;conditionally-supported behavior</B>
</P>

<P>behavior evoked by a program construct that is not a mandatory
requirement of this International Standard. If a given implementation
supports the construct, the behavior shall be as described herein;
otherwise, the implementation shall document that the construct is not
supported and shall treat a program containing an occurrence of the
construct as ill-formed (1.3.4&nbsp;



 <A HREF="intro.html#defns.ill.formed">defns.ill.formed</A>).</P>

</BLOCKQUOTE>

</LI>

<LI>

<P>Add the indicated words to 1.4&nbsp;



 <A HREF="intro.html#intro.compliance">intro.compliance</A> paragraph 2,
bullet 2:</P>

<UL>
<LI>
<P>If a program contains a violation of any diagnosable
rule,<B> or an occurrence of a construct described herein as
&ldquo;conditionally-supported&rdquo; or as resulting in
&ldquo;conditionally-supported behavior&rdquo; when the implementation
does not in fact support that construct</B>, a conforming
implementation shall issue at least one diagnostic message, except
that</P>
</LI>
</UL>

</LI>

<LI>
<P>Insert the following as a new paragraph following 5.2.10&nbsp;



 <A HREF="expr.html#expr.reinterpret.cast">expr.reinterpret.cast</A> paragraph 7:</P>

<BLOCKQUOTE>

Converting a pointer to a function to a pointer to an object type or
vice versa evokes conditionally-supported behavior. In any such
conversion supported by an implementation, converting from an rvalue
of one type to the other and back (possibly with different
cv-qualification) shall yield the original pointer value; mappings
between pointers to functions and pointers to objects are otherwise
implementation-defined.

</BLOCKQUOTE>

</LI>

<LI>
<P>Change 7.4&nbsp;



 <A HREF="dcl.html#dcl.asm">dcl.asm</A> paragraph 1 as indicated:</P>

<BLOCKQUOTE>

<S>The meaning of an</S> <B>An</B> <TT>asm</TT> declaration <B>evokes
conditionally-supported behavior.  If supported, its meaning</B> is
implementation-defined.

</BLOCKQUOTE>

</LI>

<LI>
<P>Change 7.5&nbsp;



 <A HREF="dcl.html#dcl.link">dcl.link</A> paragraph 2 as indicated:</P>

<BLOCKQUOTE>

The <I>string-literal</I> indicates the required language linkage. <S>The meaning of the
string-literal is implementation-defined. A linkage-specification with a string that
is unknown to the implementation is ill-formed.</S> <B>This International Standard
specifies the semantics of C and C++ language linkage. Other values of the
<I>string-literal</I> evoke conditionally-supported behavior, with
implementation-defined semantics. [<I>Note:</I> Therefore, a
<I>linkage-specification</I> with a <I>string-literal</I> that is
unknown to the implementation requires a diagnostic.</B> <S>When the
string-literal in a linkage-specification names a programming
language, the spelling of the programming language's name is
implementation-defined. [Note:</S> <B>It</B> is recommended that the
spelling be taken from the document defining that language, for
example <TT>Ada</TT> (not <TT>ADA</TT>) and <TT>Fortran</TT> or
<TT>FORTRAN</TT> (depending on the vintage). <S>The semantics of a
language linkage other than C++ or C are implementation-defined.</S> ]

</BLOCKQUOTE>

</LI>

<LI>
<P>Change 14&nbsp;



 <A HREF="template.html#temp">temp</A> paragraph 4 as indicated:</P>

<BLOCKQUOTE>

A template, a template explicit specialization (14.7.3&nbsp;



 <A HREF="template.html#temp.expl.spec">temp.expl.spec</A>), or a class template partial specialization shall
not have C linkage. If the linkage of one of these is something other
than C or C++, the <S>behavior is implementation-defined</S> <B>result
is conditionally-supported behavior, with implementation-defined
semantics</B>.

</BLOCKQUOTE>

</LI>

</OL>

<BR>
<BR>
<HR>
<A NAME="463"></A>
<H4>463.
  
<TT>reinterpret_cast&lt;T*&gt;(0)</TT>
</H4>
<B>Section: </B>5.2.10&nbsp;



 <A HREF="expr.html#expr.reinterpret.cast">expr.reinterpret.cast</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Gennaro Prota
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>14 Feb 2004<BR>


<P>[Voted into WP at April, 2006 meeting.]</P>

<P>Is <TT>reinterpret_cast&lt;T*&gt;(</TT><I>null_pointer_constant</I><TT>)</TT>
guaranteed to yield the
null pointer value of type T*?</P>

<P>I think a committee clarification is needed. Here's why:
5.2.10&nbsp;



 <A HREF="expr.html#expr.reinterpret.cast">expr.reinterpret.cast</A>
par. 8 talks of "null pointer value", not
"null pointer constant", so it would seem that
<PRE>
  reinterpret_cast&lt;T*&gt;(0)
</PRE>
is a normal int-&gt;T* conversion, with an implementation-defined result.</P>

<P>However a little note to
5.2.10&nbsp;



 <A HREF="expr.html#expr.reinterpret.cast">expr.reinterpret.cast</A> par. 5 says:
<BLOCKQUOTE>
   Converting an integral constant expression (5.19) with value zero
   always yields a null pointer (4.10), but converting other
   expressions that happen to have value zero need not yield a null
   pointer.
</BLOCKQUOTE>
Where is this supported in normative text? It seems that either the
footnote or paragraph 8 doesn't reflect the intent.</P>

<P>SUGGESTED RESOLUTION: I think it would be better to drop the footnote
#64 (and thus the special case for ICEs), for two reasons:</P>

<P>a) it's not normative anyway; so I doubt anyone is relying on the
guarantee it hints at, unless that guarantee is given elsewhere in a
normative part</P>

<P>b) users expect reinterpret_casts to be almost always implementation
dependent, so this special case is a surprise. After all, if one wants
a null pointer there's static_cast. And if one wants reinterpret_cast
semantics the special case requires doing some explicit cheat, such as
using a non-const variable as intermediary:</P>
<PRE>
   int v = 0;
   reinterpret_cast&lt;T*&gt;(v); // implementation defined

   reinterpret_cast&lt;T*&gt;(0); // null pointer value of type T*
   const int w = 0;
   reinterpret_cast&lt;T*&gt;(w); // null pointer value of type T*
</PRE>

<P>It seems that not only that's providing a duplicate functionality, but
also at the cost to hide what seems the more natural one.</P>

<P>
<B>Notes from October 2004 meeting:</B>
</P>

<P>This footnote was added in 1996, after the invention of
<TT>reinterpret_cast</TT>, so the presumption must be that it was
intentional.  At this time, however, the CWG feels that there is
no reason to require that <TT>reinterpret_cast&lt;T*&gt;(0)</TT>
produce a null pointer value as its result.</P>

<P>
<B>Proposed resolution (April, 2005):</B>
</P>

<OL>
<LI>
<P>Delete the footnote in 5.2.10&nbsp;



 <A HREF="expr.html#expr.reinterpret.cast">expr.reinterpret.cast</A>
paragraph 5 reading,</P>

<BLOCKQUOTE>

Converting an integral constant expression
(5.19&nbsp;



 <A HREF="expr.html#expr.const">expr.const</A>) with value zero always yields a null
pointer (4.10&nbsp;



 <A HREF="conv.html#conv.ptr">conv.ptr</A>), but converting other expressions
that happen to have value zero need not yield a null pointer.

</BLOCKQUOTE>

</LI>

<LI>
<P>Add the indicated note to 5.2.10&nbsp;



 <A HREF="expr.html#expr.reinterpret.cast">expr.reinterpret.cast</A> paragraph
8:</P>

<BLOCKQUOTE>

The null pointer value (4.10&nbsp;



 <A HREF="conv.html#conv.ptr">conv.ptr</A>) is converted to
the null pointer value of the destination type.  <B>[<I>Note:</I>
A null pointer constant, which has integral type, is not necessarily
converted to a null pointer value. &mdash;<I>end note</I>]</B>

</BLOCKQUOTE>
</LI>

</OL>

<BR>
<BR>
<HR>
<A NAME="324"></A>
<H4>324.
  
Can "<TT>&amp;</TT>" be applied to assignment to bit-field?
</H4>
<B>Section: </B>5.3.1&nbsp;



 <A HREF="expr.html#expr.unary.op">expr.unary.op</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Alasdair Grant
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>27 Nov 2001<BR>


<P>[Voted into WP at October 2003 meeting.]</P>

<P>An assignment returns an lvalue for its left operand.  If that
operand refers to a bit field, can the "<TT>&amp;</TT>" operator be
applied to the assignment?  Can a reference be bound to it?</P>
<PRE>
  struct S { int a:3; int b:3; int c:3; };

  void f()
  {
    struct S s;
    const int *p = &amp;(s.b = 0);     // (a)
    const int &amp;r = (s.b = 0);      // (b)
          int &amp;r2 = (s.b = 0);     // (c)
  }
</PRE>

<P>
<B>Notes from the 4/02 meeting:</B>
</P>

<P>The working group agreed that this should be an error.</P>

<P>
<B>Proposed resolution (October 2002):</B>
</P>

<P>
In 5.3.2&nbsp;



 <A HREF="expr.html#expr.pre.incr">expr.pre.incr</A>
paragraph 1 (prefix "<TT>++</TT>" and "<TT>--</TT>" operators), change
<BLOCKQUOTE>
The value is the new value of the operand; it is an lvalue.
</BLOCKQUOTE>
to
<BLOCKQUOTE>
The result is the updated operand; it is an lvalue, and it is a
bit-field if the operand is a bit-field.
</BLOCKQUOTE>
</P>

<P>
In 5.16&nbsp;



 <A HREF="expr.html#expr.cond">expr.cond</A>
paragraph 4 ("<TT>?</TT>" operator), add the indicated text:
<BLOCKQUOTE>
If the second and third operands are lvalues and have
the same type, the result is of that type and is an lvalue<B>
and it is a bit-field if the second or the third
operand is a bit-field, or if both are bit-fields.</B>
</BLOCKQUOTE>
</P>

<P>
In 5.17&nbsp;



 <A HREF="expr.html#expr.ass">expr.ass</A> paragraph 1 (assignment operators)
add the indicated text (the original text is
as updated by issue 221, which is DR but not in TC1):
<BLOCKQUOTE>
The assignment operator (<TT>=</TT>) and the compound assignment
operators all group right-to-left.  All require a modifiable lvalue as
their left operand and return an lvalue with the type and value of
the left operand after the assignment has taken place. <B>The result
in all cases is a bit-field if the left operand is a bit-field.</B>
</BLOCKQUOTE>
</P>

<P>
Note that issue 222 adds (non-conflicting) text at the end of
this same paragraph (5.17&nbsp;



 <A HREF="expr.html#expr.ass">expr.ass</A> paragraph 1).
</P>

<P>
In 5.18&nbsp;



 <A HREF="expr.html#expr.comma">expr.comma</A> paragraph 1 (comma operator), change:
<BLOCKQUOTE>
The type and value of the result are the type and value of the right
operand; the result is an lvalue if its right operand is.
</BLOCKQUOTE>
to
<BLOCKQUOTE>
The type and value of the result are the type and value of the right
operand; the result is an lvalue if the right operand is an lvalue,
and is a bit-field if the right operand is an lvalue and a bit-field.
</BLOCKQUOTE>
</P>

<P>Relevant related text (no changes required):</P>

<P>
5.3.1&nbsp;



 <A HREF="expr.html#expr.unary.op">expr.unary.op</A> paragraph 4:
<BLOCKQUOTE>
The operand of <TT>&amp;</TT> shall not be a bit-field.
</BLOCKQUOTE>
</P>

<P>
8.5.3&nbsp;



 <A HREF="decl.html#dcl.init.ref">dcl.init.ref</A>
paragraph 5, bullet 1, sub-bullet 1 (regarding binding
a reference to an lvalue):
<BLOCKQUOTE>
... is an lvalue (but is not a bit-field) ...
</BLOCKQUOTE>
</P>

<BR>
<BR>
<HR>
<A NAME="299"></A>
<H4>299.
  
Conversion on array bound expression in <TT>new</TT>
</H4>
<B>Section: </B>5.3.4&nbsp;



 <A HREF="expr.html#expr.new">expr.new</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mark Mitchell
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>19 Jul 2001<BR>


<P>[Voted into WP at October 2005 meeting.]</P>



<P>In 5.3.4&nbsp;



 <A HREF="expr.html#expr.new">expr.new</A>, the standard says that the
expression in an array-new has to 
have integral type.  There's already a DR (<A HREF="
     cwg_defects.html#74">issue 74</A>)
that says it should also be allowed to have enumeration type.  But, it should
probably also say that it can have a class type with a single
conversion to integral type; in other words the same thing as in
6.4.2&nbsp;



 <A HREF="stmt.html#stmt.switch">stmt.switch</A> paragraph 2.</P>

<P>
<B>Suggested resolution:</B>
</P>

<P>In 5.3.4&nbsp;



 <A HREF="expr.html#expr.new">expr.new</A> paragraph 6, replace
"integral or enumeration type (3.9.1&nbsp;



 <A HREF="basic.html#basic.fundamental">basic.fundamental</A>)" with
"integral or enumeration type (3.9.1&nbsp;



 <A HREF="basic.html#basic.fundamental">basic.fundamental</A>), or a class
type for which a single conversion function to
integral or enumeration type exists".</P>

<P>
<B>Proposed resolution (October, 2004):</B>
</P>

<P>Change 5.3.4&nbsp;



 <A HREF="expr.html#expr.new">expr.new</A> paragraph 6 as
follows:</P>

<BLOCKQUOTE>

Every <I>constant-expression</I> in a
<I>direct-new-declarator</I> shall be an integral constant
expression (5.19&nbsp;



 <A HREF="expr.html#expr.const">expr.const</A>) and evaluate to a
strictly positive value. The <I>expression</I> in a
<I>direct-new-declarator</I> shall <S>have</S> <B>be of</B>
integral type, <S>or</S> enumeration type<S> (3.9.1)</S><B>, or a
class type for which a single conversion function to integral or
enumeration type exists (12.3&nbsp;



 <A HREF="special.html#class.conv">class.conv</A>). If the
expression is of class type, the expression is converted by
calling the conversion function, and the result of the conversion
is used in place of the original expression. The value of the
expression shall be</B><S>with a</S> non-negative<S>
value</S>. [<I>Example:</I> ...

</BLOCKQUOTE>

<P>
<B>Proposed resolution (April, 2005):</B>
</P>

<P>Change 5.3.4&nbsp;



 <A HREF="expr.html#expr.new">expr.new</A> paragraph 6 as
follows:</P>

<BLOCKQUOTE>

Every <I>constant-expression</I> in a
<I>direct-new-declarator</I> shall be an integral constant
expression (5.19&nbsp;



 <A HREF="expr.html#expr.const">expr.const</A>) and evaluate to a
strictly positive value. The <I>expression</I> in a
<I>direct-new-declarator</I> shall <S>have integral or enumeration
type (3.9.1&nbsp;



 <A HREF="basic.html#basic.fundamental">basic.fundamental</A>) with a non-negative
value</S> <B>be of integral type, enumeration type, or a class type for
which a single conversion function to integral or enumeration type
exists (12.3&nbsp;



 <A HREF="special.html#class.conv">class.conv</A>). If the expression is of class
type, the expression is converted by calling that conversion function,
and the result of the conversion is used in place of the original
expression. If the value of the expression is negative, the behavior
is undefined</B>. [<I>Example:</I> ...

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="429"></A>
<H4>429.
  
Matching deallocation function chosen based on syntax or signature?
</H4>
<B>Section: </B>5.3.4&nbsp;



 <A HREF="expr.html#expr.new">expr.new</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>John Wilkinson
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>18  July 2003<BR>


<P>[Voted into WP at October 2004 meeting.]</P>

<P>What does this example do?</P>
<PRE>
  #include &lt;stdio.h&gt;
  #include &lt;stdlib.h&gt;

  struct A {
        void* operator new(size_t alloc_size, size_t dummy=0) {
                printf("A::operator new()\n");
                return malloc(alloc_size);
        };

        void operator delete(void* p, size_t s) {
                printf("A::delete %d\n", s);
        };


        A()  {printf("A constructing\n"); throw 2;};

  };

  int
  main() {
    try {
        A* ap = new A;
        delete ap;
    }
    catch(int) {printf("caught\n"); return 1;}
  }  
</PRE>

<P>The fundamental issue here is whether the deletion-on-throw
is driven by the syntax of the new (placement or non-placement)
or by signature matching.  If the former, the operator delete
would be called with the second argument equal to the size of
the class.  If the latter, it would be called with the second
argument 0.</P>

<P>
<A HREF="
     cwg_defects.html#127">Core issue 127</A> (in TC1) dealt with
this topic.  It removed some wording
in 15.2&nbsp;



 <A HREF="except.html#except.ctor">except.ctor</A> paragraph 2 that implied a
syntax-based interpretation, leaving wording
in 5.3.4&nbsp;



 <A HREF="expr.html#expr.new">expr.new</A> paragraph 19 that is
signature-based.  But there is no accompanying
rationale to confirm an explicit choice of the signature-based
approach.</P>

<P>EDG and g++ get 0 for the second argument, matching the presumed
core issue 127 resolution.  But maybe this should be revisited.</P>

<P>
<B>Notes from October 2003 meeting:</B>
</P>

<P>There was widespread agreement that the compiler shouldn't
just silently call the delete with either of the possible values.
In the end, we decided it's smarter to issue an error on this
case and force the programmer to say what he means.</P>

<P>Mike Miller's analysis of the status quo:
3.7.3.2&nbsp;



 <A HREF="basic.html#basic.stc.dynamic.deallocation">basic.stc.dynamic.deallocation</A> paragraph 2
says that "<TT>operator delete(void*, std::size_t)</TT>" is a
"usual (non-placement) deallocation function" if the class does
not declare "<TT>operator delete(void*)</TT>."
3.7.3.1&nbsp;



 <A HREF="basic.html#basic.stc.dynamic.allocation">basic.stc.dynamic.allocation</A> does not use the
same terminology for allocation functions, but the most
reasonable way to understand the uses of the term "placement
allocation function" in the Standard is as an allocation function
that has more than one parameter and thus can (but need not) be
called using the "new-placement" syntax described in
5.3.4&nbsp;



 <A HREF="expr.html#expr.new">expr.new</A>.  (In
considering <A HREF="
     cwg_defects.html#127">issue 127</A>,
the core group discussed and endorsed the
position that, "If a placement allocation function has default
arguments for all its parameters except the first, it can be
called using non-placement syntax.")</P>

<P>5.3.4&nbsp;



 <A HREF="expr.html#expr.new">expr.new</A> paragraph 19
says that any non-placement deallocation function
matches a non-placement allocation function, and that a placement
deallocation function matches a placement allocation function
with the same parameter types after the first -- i.e., a
non-placement deallocation function cannot match a placement
allocation function.  This makes sense, because non-placement
("usual") deallocation functions expect to free memory obtained
from the system heap, which might not be the case for storage
resulting from calling a placement allocation function.</P>

<P>According to this analysis, the example shows a placement
allocation function and a non-placement deallocation function, so
the deallocation function should not be invoked at all, and the
memory will just leak.</P>

<P>
<B>Proposed Resolution (October 2003):</B>
</P>

<P>Add the following text at the end of 5.3.4&nbsp;



 <A HREF="expr.html#expr.new">expr.new</A>
paragraph 19: </P>
<BLOCKQUOTE>
If the lookup finds the two-parameter form of a usual deallocation function 
(3.7.3.2&nbsp;



 <A HREF="basic.html#basic.stc.dynamic.deallocation">basic.stc.dynamic.deallocation</A>), and that function, considered as
a placement deallocation function, would have been selected as a match
for the allocation function, the program is ill-formed.
[<I>Example:</I>
<BLOCKQUOTE>
<PRE>
struct S { 
  // <I>Placement allocation function:</I>
  static void* operator new(std::size_t, std::size_t); 

  // <I>Usual (non-placement) deallocation function:</I>
  static void operator delete(void*, std::size_t); 
}; 

S* p = new (0) S; // <I>ill-formed: non-placement deallocation function matches </I>
                  // <I>placement allocation function </I>
</PRE>
</BLOCKQUOTE>
<I>--- end example]</I>
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="353"></A>
<H4>353.
  
Is deallocation routine called if destructor throws exception in delete?
</H4>
<B>Section: </B>5.3.5&nbsp;



 <A HREF="expr.html#expr.delete">expr.delete</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Duane Smith
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>30 April 2002<BR>


<P>[Voted into WP at April 2003 meeting.]</P>

<P>In a couple of comp.std.c++ threads, people have asked
whether the Standard guarantees that the deallocation function
will be called in a delete-expression if the destructor throws
an exception.  Most/all people have expressed the opinion that 
the deallocation function must be called in this case, although 
no one has been able to cite wording in the Standard supporting 
that view.</P>

<PRE>
#include &lt;new.h&gt;
#include &lt;stdio.h&gt;
#include &lt;stdlib.h&gt;

static int flag = 0;

inline 
void operator delete(void* p) throw() 
{
   if (flag)
        printf("in deallocation function\n");
   free(p);
}

struct S {
    ~S() { throw 0; }
};

void f() {
    try {
        delete new S;
    }
    catch(...) { }
}

int main() {
       flag=1;
       f();
       flag=0;
       return 0;
}
</PRE>

<P>
<B>Proposed resolution (October 2002):</B>
</P>
<P>
Add to 5.3.5&nbsp;



 <A HREF="expr.html#expr.delete">expr.delete</A> paragraph 7 the highlighted text:</P>
<BLOCKQUOTE>
The <I>delete-expression</I> will call a <I>deallocation function</I>
(3.7.3.2&nbsp;



 <A HREF="basic.html#basic.stc.dynamic.deallocation">basic.stc.dynamic.deallocation</A>)
<B>[<I>Note:</I> The deallocation function is called regardless of
whether the destructor for the object or some element of the array
throws an exception. ]</B>
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="442"></A>
<H4>442.
  
Incorrect use of null pointer constant in description of delete operator
</H4>
<B>Section: </B>5.3.5&nbsp;



 <A HREF="expr.html#expr.delete">expr.delete</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Matthias Hofmann
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>2 Dec 2003<BR>


<P>[Voted into WP at October 2005 meeting.]</P>

<P>After some discussion in comp.lang.c++.moderated we came to the conclusion
that there seems to be a defect in
5.3.5&nbsp;



 <A HREF="expr.html#expr.delete">expr.delete</A>/4, which says:</P>
<BLOCKQUOTE>
The cast-expression in a delete-expression shall be evaluated exactly once.
If the delete-expression calls the implementation deallocation function
(3.7.3.2), and if the operand of the delete expression is not the null
pointer constant, the deallocation function will deallocate the storage
referenced by the pointer thus rendering the pointer invalid. [Note: the
value of a pointer that refers to deallocated storage is indeterminate. ]
</BLOCKQUOTE>
<P>In the second sentence, the term "null pointer constant" should be changed
to "null pointer". In its present form, the passage claims that the
deallocation function will deallocate the storage refered to by a null
pointer that did not come from a null pointer constant in the delete
expression. Besides, how can the null pointer constant be the operand of a
delete expression, as "delete 0" is an error because delete requires a
pointer type or a class type having a single conversion function to a
pointer type?</P>

<P>See also <A HREF="
     cwg_defects.html#348">issue 348</A>.</P>

<P>
<B>Proposed resolution:</B>
</P>
<P>
Change the indicated sentence of
5.3.5&nbsp;



 <A HREF="expr.html#expr.delete">expr.delete</A> paragraph 4 as follows:</P>
<BLOCKQUOTE>
If the <I>delete-expression</I> calls the implementation deallocation
function (3.7.3.2&nbsp;



 <A HREF="basic.html#basic.stc.dynamic.deallocation">basic.stc.dynamic.deallocation</A>), and if
<B>the value of</B> the operand of
the delete expression is not <S>the</S> <B>a</B> null
pointer <S>constant</S>, the deallocation function will deallocate the
storage referenced by the pointer thus rendering the pointer invalid.
</BLOCKQUOTE>

<P>
<B>Notes from October 2004 meeting:</B>
</P>

<P>This wording is superseded by, and this issue will be resolved
by, the resolution of <A HREF="
     cwg_defects.html#348">issue 348</A>.</P>

<P>
<B>Proposed resolution (April, 2005):</B>
</P>

<P>This issue is resolved by the resolution of <A HREF="
     cwg_defects.html#348">issue 348</A>.</P>

<BR>
<BR>
<HR>
<A NAME="497"></A>
<H4>497.
  
Missing required initialization in example
</H4>
<B>Section: </B>5.5&nbsp;



 <A HREF="expr.html#expr.mptr.oper">expr.mptr.oper</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Giovanni Bajo
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>03 Jan 2005<BR>


<P>[Voted into WP at October 2005 meeting.]</P>

<P>5.5&nbsp;



 <A HREF="expr.html#expr.mptr.oper">expr.mptr.oper</A> paragraph 5 contains the following
example:</P>

<PRE>
    struct S {
        mutable int i;
    };
    const S cs;
    int S::* pm = &amp;S::i;   // pm<SPAN STYLE="font-family:Times"><I> refers to mutable member </I></SPAN>S::i
    cs.*pm = 88;           // <SPAN STYLE="font-family:Times"><I>ill-formed: </I></SPAN>cs<SPAN STYLE="font-family:Times"><I> is a const object</I></SPAN>
</PRE>

<P>The const object <TT>cs</TT> is not explicitly initialized,
and class <TT>S</TT> does not have a user-declared default
constructor.  This makes the code ill-formed as per
8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A> paragraph 9.</P>

<P>
<B>Proposed resolution (April, 2005):</B>
</P>

<P>Change the example in 5.5&nbsp;



 <A HREF="expr.html#expr.mptr.oper">expr.mptr.oper</A> paragraph 5 to read
as follows:</P>

<PRE>
    struct S {
        <B>S() : i(0) { }</B>
        mutable int i;
    };
    <B>void f()
    {</B>
        const S cs;
        int S::* pm = &amp;S::i;   // pm<SPAN STYLE="font-family:Times"><I> refers to mutable member </I></SPAN>S::i
        cs.*pm = 88;           // <SPAN STYLE="font-family:Times"><I>ill-formed: </I></SPAN>cs<SPAN STYLE="font-family:Times"><I> is a const object</I></SPAN>
    <B>}</B>
</PRE>

<BR>
<BR>
<HR>
<A NAME="446"></A>
<H4>446.
  
Does an lvalue-to-rvalue conversion on the "?" operator produce a temporary?
</H4>
<B>Section: </B>5.16&nbsp;



 <A HREF="expr.html#expr.cond">expr.cond</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>John Potter
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>31 Dec 2003<BR>


<P>[Voted into WP at October 2005 meeting.]</P>

<P>The problem occurs when the value of the operator is determined to
be an rvalue, the selected argument is an lvalue, the type is a class
type and a non-const member is invoked on the modifiable rvalue result.</P>
<PRE>
    struct B {
        int v;
        B (int v) : v(v) { }
        void inc () { ++ v; }
        };
    struct D : B {
        D (int v) : B(v) { }
        };

    B b1(42);
    (0 ? B(13) : b1).inc();
    assert(b1.v == 42);
</PRE>

<P>The types of the second and third operands are the same and
one is an rvalue.  Nothing changes until p6 where an lvalue to
rvalue conversion is performed on the third operand.
12.2&nbsp;



 <A HREF="special.html#class.temporary">class.temporary</A> states that an lvalue to rvalue
conversion produces a temporary and there is nothing to remove
it.  It seems clear that the assertion must pass, yet most
implementations fail.</P>

<P>There seems to be a defect in p3 b2 b1.  First, the conditions to get
here and pass the test.</P>
<BLOCKQUOTE>
  If E1 and E2 have class type, and the underlying class types are the
  same or one is a base class of the other: E1 can be converted to
  match E2 if the class of T2 is the same type as, or a base class of,
  the class of T1, and the cv-qualification of T2 is the same
  cv-qualification as, or a greater cv-qualification than, the
  cv-qualification of T1.
</BLOCKQUOTE>
<P>If both E1 and E2 are lvalues, passing the conditions here also passes
the conditions for p3 b1.  Thus, at least one is an rvalue.  The case of
two rvalues is not interesting and the action is covered by the case
when E1 is an rvalue.</P>
<PRE>
    (0 ? D(13) : b1).inc();
    assert(b1.v == 42);
</PRE>
<BLOCKQUOTE>
  E1 is changed to an rvalue of type T2 that still refers to the
  original source class object (or the appropriate subobject thereof).
  [Note: that is, no copy is made. ]
</BLOCKQUOTE>
<P>Having changed the rvalue to base type, we are back to the above case
where an lvalue to rvalue conversion is required on the third operand
at p6.  Again, most implementations fail.</P>

<P>The remaining case, E1 an lvalue and E2 an rvalue, is the defect.</P>
<PRE>
    D d1(42);
    (0 ? B(13) : d1).inc();
    assert(d1.v == 42);
</PRE>
<P>The above quote states that an lvalue of type T1 is changed to an rvalue
of type T2 without creating a temporary.  This is in contradiction to
everything else in the standard about lvalue to rvalue conversions.
Most implementations pass in spite of the defect.</P>

<P>The usual accessible and unambiguous is missing from the base class.</P>

<P>There seems to be two possible solutions.  Following other temporary
creations would produce a temporary rvalue of type T1 and change it
to an rvalue of type T2.  Keeping the no copy aspect of this bullet
intact would change the lvalue of type T1 to an lvalue of type T2.
In this case the lvalue to rvalue conversion would happen in p6 as
usual.</P>

<P>Suggested wording for p3 b2 b1</P>

<P>The base part:</P>
<BLOCKQUOTE>
  If E1 and E2 have class type, and the underlying class types are the
  same or one is a base class of the other: E1 can be converted to match
  E2 if the class of T2 is the same type as, or an accessible and
  unambiguous base class of, the class of T1, and the cv-qualification
  of T2 is the same cv-qualification as, or a greater cv-qualification
  than, the cv-qualification of T1.  If the conversion is applied:
</BLOCKQUOTE>
<P>The same type temporary version:</P>
<BLOCKQUOTE>
  If E1 is an lvalue, an lvalue to rvalue conversion is applied.  The
  resulting or original rvalue is changed to an rvalue of type T2 that
  refers to the same class object (or the appropriate subobject
  thereof).  [Note: that is, no copy is made in changing the type of
  the rvalue. ]
</BLOCKQUOTE>
<P>The never copy version:</P>
<BLOCKQUOTE>
  The lvalue(rvalue) E1 is changed to an lvalue(rvalue) of type T2
  that refers to the original class object (or the appropriate
  subobject thereof).  [Note: that is, no copy is made. ]
</BLOCKQUOTE>
<P>The test case was posted to clc++m and results for implementations
were reported.</P>
<PRE>
#include &lt;cassert&gt;
struct B {
    int v;
    B (int v) : v(v) { }
    void inc () { ++ v; }
    };
struct D : B {
    D (int v) : B(v) { }
    };
int main () {
    B b1(42);
    D d1(42);
    (0 ? B(13) : b1).inc();
    assert(b1.v == 42);
    (0 ? D(13) : b1).inc();
    assert(b1.v == 42);
    (0 ? B(13) : d1).inc();
    assert(d1.v == 42);
    }

// CbuilderX(EDG301) FFF  Rob Williscroft
// ICC-8.0           FFF  Alexander Stippler
// COMO-4.301        FFF  Alexander Stippler

// BCC-5.4           FFP  Rob Williscroft
// BCC32-5.5         FFP  John Potter
// BCC32-5.65        FFP  Rob Williscroft
// VC-6.0            FFP  Stephen Howe
// VC-7.0            FFP  Ben Hutchings
// VC-7.1            FFP  Stephen Howe
// OpenWatcom-1.1    FFP  Stephen Howe

// Sun C++-6.2       PFF  Ron Natalie

// GCC-3.2           PFP  John Potter
// GCC-3.3           PFP  Alexander Stippler

// GCC-2.95          PPP  Ben Hutchings
// GCC-3.4           PPP  Florian Weimer
</PRE>

<P>I see no defect with regards to lvalue to rvalue conversions; however,
there seems to be disagreement about what it means by implementers.
It may not be surprising because 5.16 and passing a POD struct to an
ellipsis are the only places where an lvalue to rvalue conversion
applies to a class type.  Most lvalue to rvalue conversions are on
basic types as operands of builtin operators.</P>

<P>
<B>Notes from the March 2004 meeting:</B>
</P>

<P>We decided all "?" operators that return a class rvalue should
copy the second or third operand to a temporary.  See
<A HREF="
     cwg_defects.html#86">issue 86</A>.</P>

<P>
<B>Proposed resolution (October 2004):</B>
</P>

<OL>

<LI>
<P>Change 5.16&nbsp;



 <A HREF="expr.html#expr.cond">expr.cond</A> paragraph 3 bullet 2
sub-bullet 1 as follows:</P>

<BLOCKQUOTE>

if <TT>E1</TT> and <TT>E2</TT> have class type, and the
underlying class types are the same or one is a base class of the
other: <TT>E1</TT> can be converted to match <TT>E2</TT> if the
class of <TT>T2</TT> is the same type as, or a base class of, the
class of <TT>T1</TT>, and the cv-qualification of <TT>T2</TT> is
the same cv-qualification as, or a greater cv-qualification than,
the cv-qualification of <TT>T1</TT>. If the conversion is
applied, <TT>E1</TT> is changed to an rvalue of type <TT>T2</TT>
<S>that still refers to the original source class object (or the
appropriate subobject thereof). [<I>Note:</I> that is, no copy is
made. &mdash;<I>end note</I>]</S> <B>by copy-initializing a
temporary of type <TT>T2</TT> from <TT>E1</TT> and using that
temporary as the converted operand.</B>

</BLOCKQUOTE>

</LI>

<LI>
<P>Change 5.16&nbsp;



 <A HREF="expr.html#expr.cond">expr.cond</A> paragraph 6 bullet 1 as
follows:</P>

<BLOCKQUOTE>

The second and third operands have the same type; the result is
of that type. <B>If the operands have class type, the result is an
rvalue temporary of the result type, which is copy-initialized
from either the second operand or the third operand depending on
the value of the first operand.</B>

</BLOCKQUOTE>

</LI>

<LI>
<P>Change 4.1&nbsp;



 <A HREF="conv.html#conv.lval">conv.lval</A> paragraph 2 as follows:</P>

<BLOCKQUOTE>

<S>The value contained in the object indicated by the lvalue is
the rvalue result.</S> When an lvalue-to-rvalue conversion occurs
within the operand of <TT>sizeof</TT> (5.3.3&nbsp;



 <A HREF="expr.html#expr.sizeof">expr.sizeof</A>) the value contained in the referenced object is
not accessed, since that operator does not evaluate its operand.
<B>Otherwise, if the lvalue has a class type, the conversion
copy-initializes a temporary of type <TT>T</TT> from the lvalue
and the result of the conversion is an rvalue for the temporary.
Otherwise, the value contained in the object indicated by the
lvalue is the rvalue result.</B>

</BLOCKQUOTE>

</LI>

</OL>

<P>
<I>[Note: this wording partially resolves <A HREF="
     cwg_defects.html#86">issue 86</A>.  See also <A HREF="
     cwg_active.html#462">issue 462</A>.]</I>
</P>

<BR>
<BR>
<HR>
<A NAME="366"></A>
<H4>366.
  
String literal allowed in integral constant expression?
</H4>
<B>Section: </B>5.19&nbsp;



 <A HREF="expr.html#expr.const">expr.const</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Martin v. Loewis
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>29 July 2002<BR>


<P>[Voted into WP at October 2003 meeting.]</P>

<P>According to 16.1&nbsp;



 <A HREF="cpp.html#cpp.cond">cpp.cond</A> paragraph 1, the if-group</P>
<PRE>
#if "Hello, world"
</PRE>
<P>is well-formed, since it is an integral constant expression.
Since that may not be obvious, here is why:</P>

<P>5.19&nbsp;



 <A HREF="expr.html#expr.const">expr.const</A> paragraph 1 says that an integral constant
expression may involve literals (2.13&nbsp;



 <A HREF="lex.html#lex.literal">lex.literal</A>);
"Hello, world" is a literal. It restricts
operators to not use certain type conversions; this expression does
not use type conversions. It further disallows functions, class
objects, pointers, ... - this expression is none of those, since it 
is an array.</P>

<P>However, 16.1&nbsp;



 <A HREF="cpp.html#cpp.cond">cpp.cond</A> paragraph 6 does not explain what
to do with this if-group, since
the expression evaluates neither to false(zero) nor true(non-zero).</P>

<P>
<B>Proposed resolution (October 2002):</B>
</P>

<P>Change the beginning of the second sentence of
5.19&nbsp;



 <A HREF="expr.html#expr.const">expr.const</A> paragraph 1 which currently reads
<BLOCKQUOTE>
An <I>integral constant-expression</I> can involve only literals
(2.13&nbsp;



 <A HREF="lex.html#lex.literal">lex.literal</A>), ...
</BLOCKQUOTE>
to say
<BLOCKQUOTE>
An <I>integral constant-expression</I> can involve only literals of
arithmetic types (2.13&nbsp;



 <A HREF="lex.html#lex.literal">lex.literal</A>,
3.9.1&nbsp;



 <A HREF="basic.html#basic.fundamental">basic.fundamental</A>), ...
</BLOCKQUOTE>
</P>

<BR>
<BR>
<HR>
<A NAME="457"></A>
<H4>457.
  
Wording nit on use of const variables in constant expressions
</H4>
<B>Section: </B>5.19&nbsp;



 <A HREF="expr.html#expr.const">expr.const</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mark Mitchell
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>03 Feb 2004<BR>


<P>[Voted into WP at April 2005 meeting.]</P>

<P>I'm looking at 5.19&nbsp;



 <A HREF="expr.html#expr.const">expr.const</A>.  I see:</P>
<BLOCKQUOTE> 
    An <I>integral constant-expression</I> can involve only ... const 
variables or static data
   members of integral or enumeration types initialized with constant 
expressions ...
</BLOCKQUOTE>
<P>Shouldn't that be "const non-volatile"? </P>

<P>It seems weird to say that:
<PRE>
  const volatile int i = 3;
  int j[i];
</PRE>
is valid.</P>

<P>
<U>Steve Adamczyk:</U> See <A HREF="
     cwg_defects.html#76">issue 76</A>,
which made the similar change to 7.1.5.1&nbsp;



 <A HREF="dcl.html#dcl.type.cv">dcl.type.cv</A>
paragraph 2, and probably should have changed this one as
well.</P>

<P>
<B>Proposed resolution (October, 2004):</B>
</P>

<P>Change the first sentence in the second part of 5.19&nbsp;



 <A HREF="expr.html#expr.const">expr.const</A> paragraph 1 as follows:</P>

<BLOCKQUOTE>

An <I>integral constant-expression</I> can involve only literals
of arithmetic types (2.13&nbsp;



 <A HREF="lex.html#lex.literal">lex.literal</A>, 3.9.1&nbsp;



 <A HREF="basic.html#basic.fundamental">basic.fundamental</A>), enumerators, <B>non-volatile</B>
<TT>const</TT> variables or static data members of integral or
enumeration types initialized with constant expressions
(8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A>),
non-type template parameters of integral or enumeration types,
and <TT>sizeof</TT> expressions.

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="281"></A>
<H4>281.
  
<TT>inline</TT> specifier in <TT>friend</TT> declarations
</H4>
<B>Section: </B>7.1.2&nbsp;



 <A HREF="dcl.html#dcl.fct.spec">dcl.fct.spec</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>John Spicer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>24 Apr 2001<BR>


<P>[Moved to DR at October 2002 meeting.]</P>



<P>There is currently no restriction on the use of the
<TT>inline</TT> specifier in <TT>friend</TT> declarations.  That
would mean that the following usage is permitted:</P>

<PRE>
    struct A {
        void f();
    };

    struct B {
        friend inline void A::f();
    };

    void A::f(){}
</PRE>

<P>I believe this should be disallowed because a <TT>friend</TT>
declaration in one class should not be able to change attributes of a
member function of another class.</P>

<P>More generally, I think that the <TT>inline</TT> attribute should
only be permitted in <TT>friend</TT> declarations that are definitions.</P>

<P>
<B>Notes from the 04/01 meeting:</B>
</P>

<P>The consensus agreed with the suggested resolution.  This
outcome would be similar to the resolution of
<A HREF="
     cwg_defects.html#136">issue 136</A>.</P>

<P>
<B>Proposed resolution (10/01):</B>
</P>

<P> Add to the end of 7.1.2&nbsp;



 <A HREF="dcl.html#dcl.fct.spec">dcl.fct.spec</A> paragraph 3:</P>

<BLOCKQUOTE>
If the <TT>inline</TT> specifier is used in a friend declaration, that
declaration shall be a definition or the function shall have
previously been declared inline.
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="317"></A>
<H4>317.
  
Can a function be declared inline after it has been called?
</H4>
<B>Section: </B>7.1.2&nbsp;



 <A HREF="dcl.html#dcl.fct.spec">dcl.fct.spec</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Clamage
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>14 Oct 2001<BR>


<P>[Voted into WP at October 2005 meeting.]</P>



<P>
<U>Steve Clamage</U>:
Consider this sequence of declarations:
<PRE>
  void foo() { ... }
  inline void foo();
</PRE>
The non-inline definition of foo precedes the inline declaration.
It seems to me this code should be ill-formed, but I could not find
anything in the standard to cover the situation.</P>

<P>
<U>Bjarne Stroustrup</U>:
Neither could I, so I looked in the ARM, which addressed this case (apparently 
for member function only) in some detail in 7.1.2 (pp103-104).</P>

<P>The ARM allows declaring a function inline after its initial declaration,
as long as it has not been called.</P>

<P>
<U>Steve Clamage</U>:
If the above code is valid, how about this:</P>
<PRE>
  void foo() { ... }    // define foo
  void bar() { foo(); } // use foo
  inline void foo();    // declare foo inline
</PRE>

<P>
<U>Bjarne Stroustrup</U>:
... and [the ARM] disallows declaring a function inline after it
has been called.</P>

<P>This may still be a good resolution.</P>

<P>
<U>Steve Clamage</U>:
But the situation in the ARM is the reverse:  Declare a function
inline, and define it later (with no intervening call).  That's
a long-standing rule in C++, and allows you to write member
function definitions outside the class.</P>

<P>In my example, the compiler could reasonably process the entire
function as out-of-line, and not discover the inline declaration
until it was too late to save the information necessary for inline
generation.  The equivalent of another compiler pass would be needed
to handle this situation.</P>

<P>
<U>Bjarne Stroustrup</U>:
I see, and I think your argument it conclusive.</P>

<P>
<U>Steve Clamage</U>:
I'd like to open a core issue on this point, and I recommend wording
along the lines of:  "A function defined without an inline specifier
shall not be followed by a declaration having an inline specifier."</P>

<P>I'd still like to allow the common idiom</P>
<PRE>
  class T {
    int f();
  };
  inline int T::f() { ... }
</PRE>

<P>
<U>Martin Sebor</U>:
Since the inline keyword is just a hint to the compiler, I don't see
any harm in allowing the construct. Your hypothetical compiler can
simply ignore the inline on the second declaration. On the other hand,
I feel that adding another special rule will unnecessarily complicate
the language.</P>

<P>
<U>Steve Clamage</U>:
The inline specifier is more than a hint.  You can have multiple
definitions of inline functions, but only one definition of a
function not declared inline.  In particular, suppose the above
example were in a header file, and included multiple times in
a program.</P>

<P>
<B>Proposed resolution (October, 2004):</B>
</P>

<P>Add the indicated words to 7.1.2&nbsp;



 <A HREF="dcl.html#dcl.fct.spec">dcl.fct.spec</A>
paragraph 4:</P>

<BLOCKQUOTE>

An inline function shall be defined in every translation unit in
which it is used and shall have exactly the same definition in
every case (3.2&nbsp;



 <A HREF="basic.html#basic.def.odr">basic.def.odr</A>). [<I>Note:</I> a call to
the inline function may be encountered before its definition
appears in the translation unit. &mdash;<I>end note</I>] <B>If the
definition of a function appears in a translation unit before its
first declaration as inline, the program is ill-formed.</B> If a
function with external linkage is declared inline in one
translation unit...

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="396"></A>
<H4>396.
  
Misleading note regarding use of <TT>auto</TT> for disambiguation
</H4>
<B>Section: </B>7.1.2&nbsp;



 <A HREF="dcl.html#dcl.fct.spec">dcl.fct.spec</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Herb Sutter
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>3 Jan 2003<BR>


<P>[Voted into WP at March 2004 meeting.]</P>



<P>BTW, I noticed that the following note in 7.1.1&nbsp;



 <A HREF="dcl.html#dcl.stc">dcl.stc</A>
paragraph 2 doesn't seem to have
made it onto the issues list or into the TR:</P>
<BLOCKQUOTE>
  [Note: hence, the auto specifier is almost always redundant and not
  often used; one use of auto is to distinguish a declaration-statement
  from an expression-statement (stmt.ambig) explicitly. --- end note]
</BLOCKQUOTE>
<P>I thought that this was well known to be incorrect, because using auto
does not disambiguate this. Writing:
<PRE>
  auto int f();
</PRE>
is still a declaration of a function f, just now with an error since the
function's return type may not use an auto storage class specifier. I
suppose an error is an improvement over a silent ambiguity going the
wrong way, but it's still not a solution for the user who wants to
express the other in a compilable way.</P>

<P>Proposed resolution: Replace that note with the following note:</P>
<BLOCKQUOTE>
  [Note: hence, the auto specifier is always redundant and not often
  used. --- end note]
</BLOCKQUOTE>

<P>
<U>John Spicer</U>:
I support the proposed change, but I think the disambiguation case is not the 
one that you describe.  An example of the supposed disambiguation is:</P>
<PRE>
  int i;
  int j;
  int main()
  {
    int(i);  // declares i, not reference to ::i
    auto int(j);  // declares j, not reference to ::j
  }
</PRE>
<P>
cfront would take "int(i)" as a cast of ::i, so the auto would force what it 
would otherwise treat as a statement to be considered a declaration
(cfront 3.0 warned that this would change in the future).</P>

<P>In a conforming compiler the auto is always redundant (as you say) because 
anything that could be considered a valid declaration should be treated as
one.</P>

<P>
<B>Proposed resolution (April 2003):</B>
</P>

<P>Replace 7.1.1&nbsp;



 <A HREF="dcl.html#dcl.stc">dcl.stc</A> paragraph 2
<BLOCKQUOTE>
[Note: hence, the <TT>auto</TT> specifier
is almost always redundant and not often used;
one use of <TT>auto</TT> is to distinguish
a <I>declaration-statement</I> from
an <I>expression-statement</I> (6.8&nbsp;



 <A HREF="stmt.html#stmt.ambig">stmt.ambig</A>)
explicitly. --- end note]
</BLOCKQUOTE>
with
<BLOCKQUOTE>
[Note: hence, the <TT>auto</TT> specifier
is always redundant and not often used.
One use of <TT>auto</TT> is to distinguish
a <I>declaration-statement</I> from an <I>expression-statement</I>
explicitly
rather than relying on the disambiguation rules
(6.8&nbsp;



 <A HREF="stmt.html#stmt.ambig">stmt.ambig</A>),
which may aid readers.
--- end note]
</BLOCKQUOTE>
</P>

<BR>
<BR>
<HR>
<A NAME="424"></A>
<H4>424.
  
Wording problem with issue 56 resolution on redeclaring typedefs in class scope
</H4>
<B>Section: </B>7.1.3&nbsp;



 <A HREF="dcl.html#dcl.typedef">dcl.typedef</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Daveed Vandevoorde
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>25 June 2003<BR>


<P>[Voted into WP at March 2004 meeting.]</P>

<P>I wonder if perhaps the <A HREF="
     cwg_defects.html#56">core issue 56</A>
change in 7.1.3&nbsp;



 <A HREF="dcl.html#dcl.typedef">dcl.typedef</A> paragraph 2
wasn't quite careful enough.  The intent was to remove
the allowance for:</P>
<PRE>
  struct S {
    typedef int I;
    typedef int I;
  };
</PRE>
<P>but I think it also disallows the following:</P>
<PRE>
  class B {
    typedef struct A {} A;
    void f(struct B::A*p);
  };
</PRE>

<P>See also <A HREF="
     cwg_active.html#407">issue 407</A>.</P>

<P>
<B>Proposed resolution (October 2003):</B>
</P>

<P>At the end of 7.1.3&nbsp;



 <A HREF="dcl.html#dcl.typedef">dcl.typedef</A>
paragraph 2, add the following:</P>
<BLOCKQUOTE>
In a given class scope, a <TT>typedef</TT> specifier can be used to redefine 
any <I>class-name</I> declared in that scope that is not
also a <I>typedef-name</I>
to refer to the type to which it already refers. [<I>Example:</I>
<PRE>
  struct S {
    typedef struct A {} A;  // OK
    typedef struct B B;     // OK
    typedef A A;            // error
  };
</PRE>
]
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="283"></A>
<H4>283.
  
Template <I>type-parameter</I>s are not syntactically <I>type-name</I>s
</H4>
<B>Section: </B>7.1.5.2&nbsp;



 <A HREF="dcl.html#dcl.type.simple">dcl.type.simple</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Clark Nelson
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>01 May 2001<BR>


<P>[Voted into WP at April 2003 meeting.]</P>

<P>Although 14.1&nbsp;



 <A HREF="template.html#temp.param">temp.param</A> paragraph 3 contains an
assertion that</P>

<BLOCKQUOTE>

A <I>type-parameter</I> defines its identifier to be a
<I>type-name</I> (if declared with <TT>class</TT> or
<TT>typename</TT>)

</BLOCKQUOTE>

<P>the grammar in 7.1.5.2&nbsp;



 <A HREF="dcl.html#dcl.type.simple">dcl.type.simple</A> paragraph 1
says that a <I>type-name</I> is either a <I>class-name</I>, an
<I>enum-name</I>, or a <I>typedef-name</I>.  The <I>identifier</I>
in a template <I>type-parameter</I> is none of those.  One
possibility might be to equate the <I>identifier</I> with a
<I>typedef-name</I> instead of directly with a <I>type-name</I>,
which would have the advantage of not requiring parallel treatment
of the two in situations where they are treated the same (e.g.,
in <I>elaborated-type-specifier</I>s, see
<A HREF="
     cwg_defects.html#245">issue 245</A>).  See also
<A HREF="
     cwg_active.html#215">issue 215</A>.</P>

<P>
<B>Proposed resolution (Clark Nelson, March 2002):</B>
</P>

<P>In 14.1&nbsp;



 <A HREF="template.html#temp.param">temp.param</A> paragraph 3,
change "A <I>type-parameter</I> defines its identifier to be a
<I>type-name</I>"
to "A <I>type-parameter</I> defines its identifier
to be a <I>typedef-name</I>"</P>

<P>In 7.1.5.3&nbsp;



 <A HREF="dcl.html#dcl.type.elab">dcl.type.elab</A> paragraph 2,
change "If the identifier resolves to a <I>typedef-name</I> or a template
<I>type-parameter</I>"
to "If the identifier resolves to a <I>typedef-name</I>".</P>

<P>This has been consolidated with the edits for some other
issues.  See N1376=02-0034.</P>

<BR>
<BR>
<HR>
<A NAME="172"></A>
<H4>172.
  
Unsigned int as underlying type of enum
</H4>
<B>Section: </B>7.2&nbsp;



 <A HREF="dcl.html#dcl.enum">dcl.enum</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Bjarne Stroustrup
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>26 Sep 1999<BR>



<P>[Moved to DR at October 2002 meeting.]</P>



<P>According to 7.2&nbsp;



 <A HREF="dcl.html#dcl.enum">dcl.enum</A>
 paragraph 5,
the underlying type of an enum is an unspecified integral type,
which could potentially be <TT>unsigned int</TT>.  The promotion
rules in 4.5&nbsp;



 <A HREF="conv.html#conv.prom">conv.prom</A>
 paragraph 2 say
that such an enumeration value used in an expression will be promoted
to <TT>unsigned int</TT>.  This means that a conforming
implementation could give the value <TT>false</TT> for the
following code:</P>

<PRE>
    enum { zero };
    -1 &lt; zero;       // might be false
</PRE>

This is counterintuitive.  Perhaps the description of the underlying
type of an enumeration should say that an unsigned underlying type
can be used only if the values of the enumerators cannot be
represented in the corresponding signed type.  This approach would
be consistent with the treatment of integral promotion of
bitfields (4.5&nbsp;



 <A HREF="conv.html#conv.prom">conv.prom</A>
 paragraph 3).

<P>On a related note,
7.2&nbsp;



 <A HREF="dcl.html#dcl.enum">dcl.enum</A>
 paragraph 5 says,</P>

<BLOCKQUOTE>
the underlying type shall not be larger than <TT>int</TT> unless
the value of an enumerator cannot fit in an <TT>int</TT> or
<TT>unsigned int</TT>.
</BLOCKQUOTE>

<P>This specification does not allow for an enumeration like</P>

<PRE>
    enum { a = -1, b = UINT_MAX };
</PRE>

<P>Since each enumerator can fit in an <TT>int</TT>
or <TT>unsigned int</TT>, the underlying type is required to be
no larger than <TT>int</TT>, even though there is no such type that
can represent all the enumerators.</P>

<P>
<B>Proposed resolution (04/01; obsolete, see below):</B>
</P>

<P>Change 7.2&nbsp;



 <A HREF="dcl.html#dcl.enum">dcl.enum</A> paragraph 5 as follows:</P>

<BLOCKQUOTE>

It is implementation-defined which integral type is used as
the underlying type for an enumeration except that the
underlying type shall not be larger than <TT>int</TT> unless
<S>the value of an enumerator cannot fit in an <TT>int</TT>
or <TT>unsigned int</TT></S> <B>neither <TT>int</TT> nor
<TT>unsigned int</TT> can represent all the enumerator values.
Furthermore, the underlying type shall not be an unsigned
type if the corresponding signed type can represent all the
enumerator values.</B>

</BLOCKQUOTE>

<P>See also <A HREF="
     cwg_defects.html#58">issue 58</A>.</P>

<P>
<B>Notes from 04/01 meeting:</B>
</P>

<P>It was noted that 4.5&nbsp;



 <A HREF="conv.html#conv.prom">conv.prom</A> promotes unsigned
types smaller than <TT>int</TT> to (signed) <TT>int</TT>.  The
signedness chosen by an implementation for small underlying types
is therefore unobservable, so the last sentence of the proposed
resolution above should apply only to <TT>int</TT> and larger
types.  This observation also prompted discussion of an
alternative approach to resolving the issue, in which the
<I>b<sub>min</sub></I> and <I>b<sub>max</sub></I> of the enumeration
would determine the promoted type rather than the underlying type.

</P>

<P>
<B>Proposed resolution (10/01):</B>
</P>

<P>Change 4.5&nbsp;



 <A HREF="conv.html#conv.prom">conv.prom</A> paragraph 2 from
<BLOCKQUOTE>
An rvalue of type <TT>wchar_t</TT> (3.9.1&nbsp;



 <A HREF="basic.html#basic.fundamental">basic.fundamental</A>)
or an enumeration type
(7.2&nbsp;



 <A HREF="dcl.html#dcl.enum">dcl.enum</A>) can be converted to an rvalue of
the first of the following
types  that  can represent all the values of its underlying type:
<TT>int</TT>, <TT>unsigned int</TT>, <TT>long</TT>, or <TT>unsigned long</TT>.
</BLOCKQUOTE>
to
<BLOCKQUOTE>
An rvalue of type <TT>wchar_t</TT> (3.9.1&nbsp;



 <A HREF="basic.html#basic.fundamental">basic.fundamental</A>)
can be converted to an rvalue of the first of the following
types  that  can represent all the values of its underlying type:
<TT>int</TT>, <TT>unsigned int</TT>, <TT>long</TT>, or <TT>unsigned long</TT>.
An rvalue of an enumeration type (7.2&nbsp;



 <A HREF="dcl.html#dcl.enum">dcl.enum</A>)
can be converted to an rvalue of the first of the following
types  that  can represent all the values of the enumeration (i.e., the
values in the range <I>b<SUB>min</SUB></I> to <I>b<SUB>max</SUB></I> as
described in 7.2&nbsp;



 <A HREF="dcl.html#dcl.enum">dcl.enum</A>):
<TT>int</TT>, <TT>unsigned int</TT>, <TT>long</TT>, or <TT>unsigned long</TT>.
</BLOCKQUOTE>
</P>

<BR>
<BR>
<HR>
<A NAME="377"></A>
<H4>377.
  
Enum whose enumerators will not fit in any integral type
</H4>
<B>Section: </B>7.2&nbsp;



 <A HREF="dcl.html#dcl.enum">dcl.enum</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mark Mitchell
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>30 August 2002<BR>


<P>[Voted into WP at April 2003 meeting.]</P>

<P>7.2&nbsp;



 <A HREF="dcl.html#dcl.enum">dcl.enum</A> defines the underlying type of an
enumeration as an integral type "that can represent all the enumerator
values defined in the enumeration".</P>

<P>What does the standard say about this code:</P>
<PRE>
  enum E { a = LONG_MIN, b = ULONG_MAX };
</PRE>
<P>?</P>

<P>I think this should be ill-formed.</P>

<P>
<B>Proposed resolution:</B>
</P>

<P>In 7.2&nbsp;



 <A HREF="dcl.html#dcl.enum">dcl.enum</A> paragraph 5 after
<BLOCKQUOTE>
The <I>underlying</I> <I>type</I> of an enumeration is an integral type
that can represent all the enumerator values defined in the enumeration.
</BLOCKQUOTE>
insert
<BLOCKQUOTE>
If no integral type can represent all the enumerator values,
the enumeration is ill-formed.
</BLOCKQUOTE>
</P>

<BR>
<BR>
<HR>
<A NAME="518"></A>
<H4>518.
  
Trailing comma following <I>enumerator-list</I>
</H4>
<B>Section: </B>7.2&nbsp;



 <A HREF="dcl.html#dcl.enum">dcl.enum</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Charles Bryant
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>10 May 2005<BR>


<P>[Voted into WP at April, 2006 meeting.]</P>

<P>The C language (since C99), and some C++ compilers, accept:</P>

<PRE>
    enum { FOO, };
</PRE>

<P>as syntactically valid. It would be useful</P>

<UL>

<LI>
<P>for machine generated code</P>
</LI>

<LI>
<P>for minimising changes when editing</P>
</LI>

<LI>
<P>to allow a distinction between the final item being intended as
an ordinary item or as a limit:</P>
</LI>

<PRE>
  enum { red, green, blue, num_colours };  // note no comma
  enum { fred, jim, sheila, };             // last is not special
</PRE>

</UL>

<P>This proposed change is to permit a trailing comma in enum by adding:</P>

<BLOCKQUOTE>

<TT>enum</TT> <I>identifier<SUB>opt</SUB></I> <TT>{</TT> <I>enumerator-list</I> <TT>,</TT> <TT>}</TT> 

</BLOCKQUOTE>

<P>as an alternative definition for the <I>enum-specifier</I> nonterminal
in <secton_ref>7.2&nbsp;



 <A HREF="dcl.html#dcl.enum">dcl.enum</A></secton_ref> paragraph 1.</P>

<P>
<B>Proposed resolution (October, 2005):</B>
</P>

<P>Change the grammar in 7.2&nbsp;



 <A HREF="dcl.html#dcl.enum">dcl.enum</A> paragraph 1 as
indicated:</P>

<BLOCKQUOTE>

<I>enum-specifier:</I>
<UL>
<TT>enum</TT> <I>identifier<SUB>opt</SUB> </I><TT>{</TT><I> enumerator-list<SUB>opt</SUB> </I><TT>}</TT>
</UL>
<B>
<UL>
<TT>enum</TT> <I>identifier<SUB>opt</SUB> </I><TT>{</TT><I> enumerator-list </I><TT>,</TT> <TT>}</TT>
</UL>
</B>

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="11"></A>
<H4>11.
  
How do the keywords typename/template interact with using-declarations?
</H4>
<B>Section: </B>7.3.3&nbsp;



 <A HREF="dcl.html#namespace.udecl">namespace.udecl</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Bill Gibbons
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>unknown<BR>



<P>[Voted into WP at March 2004 meeting.]</P>



<P>
<B><U>Issue 1:</U></B>
</P>

<P>The working paper is not clear about how the typename/template keywords
interact with using-declarations:</P>
<PRE>
     template&lt;class T&gt; struct A {
         typedef int X;
     };
     
     template&lt;class T&gt; void f() {
         typename A&lt;T&gt;::X a;      // OK
         using typename A&lt;T&gt;::X;  // OK
         typename X b;  // ill-formed; X must be qualified
         X c;  // is this OK?
     }
</PRE>
When the rules for <TT>typename</TT> and the similar use of <TT>template</TT>
were decided, we chose to require that they be used at every reference.
The way to avoid <TT>typename</TT> at every use is to declare a typedef;
then the typedef name itself is known to be a type. For <I>using-declaration</I>s,
we decided that they do not introduce new declarations but rather are aliases
for existing declarations, like symbolic links. This makes it unclear whether
the declaration "<TT>X c;</TT>" above should be well-formed, because there
is no new name declared so there is no declaration with a "this is a type"
attribute. (The same problem would occur with the <TT>template</TT> keyword
when a member template of a dependent class is used). I think these are
the main options:
<OL>
<LI>
Continue to allow <TT>typename</TT> in <I>using-declaration</I>s, and <TT>template</TT>
(for member templates) too. Attach the "is a type" or "is a template"
attribute to the placeholder name which the using-declaration "declares"</LI>

<LI>
Disallow <TT>typename</TT> and <TT>template</TT> in <I>using-declaration</I>s
(just as <I>class-key</I>s are disallowed now). Allow <TT>typename</TT>
and <TT>template</TT> before unqualified names which refer to dependent
qualified names through <I>using-declaration</I>s.</LI>

<LI>
Document that this is broken.</LI>
</OL>
<B>Suggested Resolution:</B>

<P>The core WG already resolved this issue according to (1), but the wording
does not seem to have been added to the standard. New wording needs to
be drafted.</P>

<P>
<B><U>Issue 2:</U></B>
</P>

<P>Either way, one more point needs clarification. If the first option
is adopted:</P>
<PRE>
     template&lt;class T&gt; struct A {
         struct X { };
     };
     
     template&lt;class T&gt; void g() {
         using typename A&lt;T&gt;::X;
         X c;    // if this is OK, then X by itself is a  type
         int X;  // is this OK?
     }
</PRE>
When "<TT>g</TT>" is instantiated, the two declarations of <TT>X</TT> are compatible
(7.3.3&nbsp;



 <A HREF="dcl.html#namespace.udecl">namespace.udecl</A>
 paragraph 10).
But there is no way to know this when the definition of "<TT>g</TT>" is
compiled. I think this case should be ill-formed under the first option.
(It cannot happen under the second option.) If the second option is adopted:
<PRE>
     template&lt;class T&gt; struct A {
         struct X { };
     };
     
     template&lt;class T&gt; void g() {
         using A&lt;T&gt;::X;
         int X;  // is this OK?
     }
</PRE>
Again, the instantiation would work but there is no way to know that in
the template definition. I think this case should be ill-formed under the
second option. (It would already be ill-formed under the first option.)

<P>From John Spicer:</P>
<BLOCKQUOTE>The "not a new declaration" decision is more of a guiding principle
than a hard and fast rule. For example, a name introduced in a 
<I>using-declaration</I>
can have different access than the original declaration.

<P>Like symbolic links, a <I>using-declaration</I> can be viewed as a declaration
that declares an alias to another name, much like a typedef.</P>

<P>In my opinion, "<TT>X c;</TT>" is already well-formed. Why would we permit
<TT>typename</TT> to be used in a <I>using-declaration</I> if not to permit this
precise usage?</P>

<P>In my opinion, all that needs to be done is to clarify that the "typeness"
or "templateness" attribute of the name referenced in the <I>using-declaration</I>
is attached to the alias created by the <I>using-declaration</I>. This is
solution #1.</P>
</BLOCKQUOTE>
<B>Tentative Resolution:</B>

<P>The rules for multiple declarations with the same name in the same scope
should treat a <I>using-declaration</I> which names a type as a typedef,
just as a typedef of a class name is treated as a class declaration. This
needs drafting work. Also see <A HREF="
     cwg_active.html#36">Core issue 36</A>.</P>

<P>
<B>Rationale (04/99):</B> Any semantics associated with the
<TT>typename</TT> keyword in <I>using-declaration</I>s should be considered an
extension.</P>

<P>
<B>Notes from the April 2003 meeting:</B>
</P>

<P>This was reopened because we are now considering extensions again.
We agreed that it is desirable for the typename to be "sticky" on
a using-declaration, i.e., references to the name introduced by
the using-declaration are known to be type names without the use
of the typename keyword (which can't be specified on an unqualified
name anyway, as of now).  The related issue with the template keyword
already has a separate issue <A HREF="
     cwg_closed.html#109">109</A>.</P>

<P>Issue 2 deals with the "struct hack."
There is an example in 7.3.3&nbsp;



 <A HREF="dcl.html#namespace.udecl">namespace.udecl</A> paragraph 10
that shows a use of using-declarations to import two names that
coexist because of the "struct hack."  After some deliberation,
we decided that the template-dependent using-declaration case is
different enough that we did not have to support the "struct hack"
in that case.
A name introduced in such a case is like a typedef, and no other
hidden type can be accessed through an elaborated type specifier.</P>

<P>
<B>Proposed resolution (April 2003, revised October 2003):</B>
</P>

<P>Add a new paragraph to the bottom of 7.3.3&nbsp;



 <A HREF="dcl.html#namespace.udecl">namespace.udecl</A>:</P>

<BLOCKQUOTE>
If a <I>using-declaration</I> uses
the keyword <TT>typename</TT> and specifies a dependent name
(14.6.2&nbsp;



 <A HREF="template.html#temp.dep">temp.dep</A>), the
name introduced by the <I>using-declaration</I> is treated as a
<I>typedef-name</I> (7.1.3&nbsp;



 <A HREF="dcl.html#dcl.typedef">dcl.typedef</A>).
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="258"></A>
<H4>258.
  
<I>using-declaration</I>s and cv-qualifiers
</H4>
<B>Section: </B>7.3.3&nbsp;



 <A HREF="dcl.html#namespace.udecl">namespace.udecl</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Liam Fitzpatrick
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>2 Nov 2000<BR>


<P>[Voted into WP at April 2003 meeting.]</P>



<P>According to 7.3.3&nbsp;



 <A HREF="dcl.html#namespace.udecl">namespace.udecl</A> paragraph 12,</P>

<BLOCKQUOTE>

When a <I>using-declaration</I> brings names from a base class into a
derived class scope, member functions in the derived class override
and/or hide member functions with the same name and parameter types in
a base class (rather than conflicting).

</BLOCKQUOTE>

<P>Note that this description says nothing about the cv-qualification
of the hiding and hidden member functions.  This means, for instance,
that a non-const member function in the derived class hides a const
member function with the same name and parameter types instead of
overloading it in the derived class scope.  For example,</P>

<PRE>
    struct A {
      virtual int f() const;
      virtual int f();
    };
    struct B: A {
      B();
      int f();
      using A::f;
    };

    const B cb;
    int i = cb.f(); // ill-formed: A::f() const hidden in B

</PRE>

<P>The same terminology is used in 10.3&nbsp;



 <A HREF="derived.html#class.virtual">class.virtual</A>
paragraph 2:</P>

<BLOCKQUOTE>

If a virtual member function <TT>vf</TT> is declared in a class
<TT>Base</TT> and in a class <TT>Derived</TT>, derived directly or
indirectly from <TT>Base</TT>, a member function <TT>vf</TT> with the
same name and same parameter list as <TT>Base::vf</TT> is declared,
then <TT>Derived::vf</TT> is also virtual (whether or not it is so
declared) and it overrides <TT>Base::vf</TT>.

</BLOCKQUOTE>

<P>
<B>Notes on the 04/01 meeting:</B>
</P>

<P> The hiding and overriding should
be on the basis of the function signature, which includes any
cv-qualification on the function.</P>

<P>
<B>Proposed resolution (04/02):</B>
</P>

<P>In 7.3.3&nbsp;



 <A HREF="dcl.html#namespace.udecl">namespace.udecl</A> paragraph 12 change:
<BLOCKQUOTE>
When a <I>using-declaration</I> brings names from a base class into a
derived class scope, member functions in the derived class override and/or
hide member functions with the same name and parameter types in a base
class (rather than conflicting).
</BLOCKQUOTE>
to read:
<BLOCKQUOTE>
When a <I>using-declaration</I> brings names from a base class into a
derived class scope, member functions and member function templates in
the derived class override and/or hide member functions and member
function templates with the same name, parameter-type-list
(8.3.5&nbsp;



 <A HREF="decl.html#dcl.fct">dcl.fct</A>),
and <I>cv</I>-qualification in a base class (rather than conflicting).
</BLOCKQUOTE>
</P>
<P>
In 10.3&nbsp;



 <A HREF="derived.html#class.virtual">class.virtual</A> paragraph 2 change:
<BLOCKQUOTE>
If a virtual member function <TT>vf</TT> is declared in a class
<TT>Base</TT> and in a class <TT>Derived</TT>, derived directly or
indirectly from <TT>Base</TT>, a member function <TT>vf</TT> with the
same name and same parameter list as <TT>Base::vf</TT> is declared,
then <TT>Derived::vf</TT> is also virtual (whether or not it is so
declared) and it overrides <TT>Base::vf</TT>.
</BLOCKQUOTE>
to read:
<BLOCKQUOTE>
If a virtual member function <TT>vf</TT> is declared in a class
<TT>Base</TT> and in a class <TT>Derived</TT>, derived directly or
indirectly from <TT>Base</TT>, a member function <TT>vf</TT> with the
same name, parameter-type-list (8.3.5&nbsp;



 <A HREF="decl.html#dcl.fct">dcl.fct</A>), and
<I>cv</I>-qualification as <TT>Base::vf</TT>
is declared, then <TT>Derived::vf</TT> is also virtual (whether or not
it is so declared) and it overrides <TT>Base::vf</TT>.
</BLOCKQUOTE>
</P>

<P>See <A HREF="
     cwg_defects.html#140">issue 140</A> for the definition of
<I>parameter-type-list</I>.</P>
<BR>
<BR>
<HR>
<A NAME="460"></A>
<H4>460.
  
Can a <I>using-declaration</I> name a namespace?
</H4>
<B>Section: </B>7.3.3&nbsp;



 <A HREF="dcl.html#namespace.udecl">namespace.udecl</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>John Spicer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>12 Feb 2004<BR>


<P>[Voted into WP at April 2005 meeting.]</P>

<P>Can a using-declaration be used to import a namespace?</P>
<PRE>
namespace my_namespace{
  namespace my_namespace2 {
    int function_of_my_name_space(){ return 2;}
  }
}

int main (){
  using  ::my_namespace::my_namespace2;
  return my_namespace2::function_of_my_name_space();
}
</PRE>
<P>Several popular compilers give an error on this, but there
doesn't seem to be anything in 7.3.3&nbsp;



 <A HREF="dcl.html#namespace.udecl">namespace.udecl</A> that
prohibits it.  It should be noted that the user can get the same
effect by using a namespace alias:</P>
<PRE>
  namespace my_namespace2 = ::my_namespace::my_namespace2;
</PRE>

<P>
<B>Notes from the March 2004 meeting:</B>
</P>

<P>We agree that it should be an error.</P>

<P>
<B>Proposed resolution (October, 2004):</B>
</P>

<P>Add the following as a new paragraph after 7.3.3&nbsp;



 <A HREF="dcl.html#namespace.udecl">namespace.udecl</A> paragraph 5:</P>

<BLOCKQUOTE>

A <I>using-declaration</I> shall not name a namespace;

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="4"></A>
<H4>4.
  
Does extern "C" affect the linkage of function names with internal linkage?
</H4>
<B>Section: </B>7.5&nbsp;



 <A HREF="dcl.html#dcl.link">dcl.link</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Anderson
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>unknown<BR>



<P>[Moved to DR at 4/01 meeting.]</P>



<P>7.5&nbsp;



 <A HREF="dcl.html#dcl.link">dcl.link</A>
 paragraph 6 says the following:</P>
<UL>At most one of a set of overloaded functions with a particular name
can have C linkage.</UL>
Does this apply to static functions as well? For example, is the following
well-formed?
<PRE>
        extern "C" {
            static void f(int) {}
            static void f(float) {}
        };
</PRE>
Can a function with internal linkage "have C linkage" at all (assuming
that phrase means "has extern "C" linkage"), for how can a function be
extern "C" if it's not extern? The function <B>type</B> can have extern
"C" linkage &mdash; but I think that's independent of the linkage of the function
<B>name</B>. It should be perfectly reasonable to say, in the example above,
that extern "C" applies only to the types of <TT>f(int)</TT> and <TT>f(float)</TT>,
not to the function names, and that the rule in 7.5&nbsp;



 <A HREF="dcl.html#dcl.link">dcl.link</A>
 paragraph 6 doesn't apply.
<P>
<B>Suggested  resolution:</B> The extern "C" linkage specification applies
only to the type of functions with internal linkage, and therefore some
of the rules that have to do with name overloading don't apply.</P>

<P>
<B>Proposed Resolution:</B>
</P>

<P>The intent is to distingush <I>implicit</I> linkage from explicit linkage
for both name linkage and language (function type) linkage. (It might
be more clear to use the terms <I>name linkage</I> and <I>type linkage</I>
to distinguish these concepts. A function can have a name with one
kind of linkage and a type with a different kind of linkage. The
function itself has no linkage: it has no name, only the declaration has
a name. This becomes more obvious when you consider function pointers.)</P>

<P>The tentatively agreed proposal is to apply implicit linkage to names
declared in brace-enclosed linkage specifications and to non-top-level
names declared in simple linkage specifications; and to apply explicit
linkage to top-level names declared in simple linkage specifications.</P>

<P>The language linkage of any function type formed through a function
declarator is that of the nearest enclosing <I>linkage-specification</I>.
For purposes of determining whether the declaration of a namespace-scope
name matches a previous declaration, the language linkage portion of the
type of a function declaration (that is, the language linkage of the function
itself, not its parameters, return type or exception specification) is
ignored.</P>

<P>For a <I>linkage-specification</I> using braces, i.e.</P>
<BLOCKQUOTE>
<TT>extern</TT> <I>string-literal</I> <TT>{</TT> <I>declaration-seq</I><SUB>opt</SUB>
<TT>}</TT>
</BLOCKQUOTE>
the linkage of any declaration of a namespace-scope name (including local
externs) which is not contained in a nested <I>linkage-specification</I>,
is not declared to have no linkage (static), and does not match a previous
declaration is given the linkage specified in the <I>string-literal.</I>
The language linkage of the type of any function declaration of a namespace-scope
name (including local externs) which is not contained in a nested <I>linkage-specification</I>
and which is declared with function declarator syntax is the same as that
of a matching previous declaration, if any, else is specified by <I>string-literal</I>.

<P>For a <I>linkage-specification</I> without braces, i.e.</P>
<BLOCKQUOTE>
<TT>extern</TT> <I>string-literal</I> <I>declaration</I>
</BLOCKQUOTE>
<P>the linkage of the names declared in the top-level declarators of <I>declaration</I>
is specified by <I>string-literal</I>; if this conflicts with the linkage
of any matching previous declarations, the program is ill-formed. The language
linkage of the type of any top-level function declarator is specified by
<I>string-literal</I>; if this conflicts with the language linkage of the
type of any matching previous function declarations, the program is ill-formed.
The effect of the <I>linkage-specification</I> on other (non top-level)
names declared in <I>declaration</I> is the same as that of the brace-enclosed
form.</P>



<P>
<U>Bill Gibbons</U>: In particular, these should be well-formed:</P>

<PRE>
    extern "C" void f(void (*fp)());   // parameter type is pointer to
                                       // function with C language linkage
    extern "C++" void g(void (*fp)()); // parameter type is pointer to
                                       // function with C++ language linkage

    extern "C++" {                     // well-formed: the linkage of "f"
        void f(void(*fp)());           // and the function type used in the
    }                                  // parameter still "C"

    extern "C" {                       // well-formed: the linkage of "g"
        void g(void(*fp)());           // and the function type used in the
    }                                  // parameter still "C++"
</PRE>

<P>but these should not:</P>

<PRE>
    extern "C++" void f(void(*fp)());  // error - linkage of "f" does not
                                       // match previous declaration
                                       // (linkage of function type used in
                                       // parameter is still "C" and is not
                                       // by itself ill-formed)
    extern "C" void g(void(*fp)());    // error - linkage of "g" does not
                                       // match previous declaration
                                       // (linkage of function type used in
                                       // parameter is still "C++" and is not
                                       // by itself ill-formed)
</PRE>

<P>That is, non-top-level declarators get their linkage from matching
declarations, if any, else from the nearest enclosing linkage
specification.  (As already described, top-level declarators in a
brace-enclosed linkage specification get the linkage from matching
declarations, if any, else from the linkage specifcation; while
top-level declarators in direct linkage specifications get their
linkage from that specification.)</P>

<P>
<U>Mike Miller</U>: This is a pretty significant change from the
current specification, which treats the two forms of language linkage
similarly for most purposes.  I don't understand why it's desirable to
expand the differences.</P>

<P>It seems very unintuitive to me that you could have a top-level
declaration in an <TT>extern "C"</TT>  block that would <I>not</I>
receive "C" linkage.</P>

<P>In the current standard, the statement in
7.5&nbsp;



 <A HREF="dcl.html#dcl.link">dcl.link</A> paragraph 4 that</P>

<BLOCKQUOTE>

the specified language linkage applies to the function types of all
function declarators, function names, and variable names introduced by
the declaration(s)

</BLOCKQUOTE>

<P>applies to both forms.  I would thus expect that in</P>

<PRE>
    extern "C" void f(void(*)());
    extern "C++" {
        void f(void(*)());
    }
    extern "C++" f(void(*)());
</PRE>

<P>both "C++" declarations would be well-formed, declaring an
overloaded version of <TT>f</TT> that takes a pointer to a "C++"
function as a parameter.  I wouldn't expect that either declaration
would be a redeclaration (valid or invalid) of the "C" version of
<TT>f</TT>.</P>

<P>
<U>Bill Gibbons</U>: The potential difficulty is the matching
process and the handling of deliberate overloading based on language
linkage.  In the above examples, how are these two declarations
matched:</P>

<PRE>
    extern "C" void f(void (*fp1)());

    extern "C++" {
        void f(void(*fp2)());
    }
</PRE>

<P>given that the linkage that is part of fp1 is "C" while the linkage (prior
to the matching process) that is part of fp2 is "C++"?</P>

<P>The proposal is that the linkage which is part of the parameter type is not
determined until after the match is attempted.  This almost always correct
because you can't overload "C" and "C++" functions; so if the function names
match, it is likely that the declarations are supposed to be the
same.</P>

<P>
<U>Mike Miller</U>: This seems like more trouble than it's worth.
This comparison of function types ignoring linkage specifications is,
as far as I know, not found anywhere in the current standard.  Why do
we need to invent it?</P>

<P>
<U>Bill Gibbons</U>: It is possible to construct pathological cases where this fails, e.g.</P>

<PRE>
    extern "C" typedef void (*PFC)();  // pointer to "C" linkage function
    void f(PFC);         // parameter is pointer to "C" function
    void f(void (*)());  // matching declaration or overload based on
                         // difference in linkage type?
</PRE>

<P>It is reasonable to require explicit typedefs in this case so that
in the above example the second function declaration gets its parameter type
function linkage from the first function declaration.</P>

<P>(In fact, I think you can't get into this situation without having already
used typedefs to declare different language linkage for the top-level and
parameter linkages.)</P>

<P>For example, if the intent is to overload based on linkage a
typedef is needed:</P>

<PRE>
    extern "C" typedef void (*PFC)();  // pointer to "C" linkage function
    void f(PFC);              // parameter is pointer to "C" function
    typedef void (*PFCPP)();  // pointer to "C++" linkage function
    void f(PFCPP);            // parameter is pointer to "C++" function
</PRE>

<P>In this case the two function declarations refer to different
functions.</P>

<P>
<U>Mike Miller</U>: This seems pretty strange to me.  I think it
would be simpler to determine the type of the parameter based on the
containing linkage specification (implicitly "C++") and require a
typedef if the user wants to override the default behavior.  For
example:</P>

<PRE>
    extern "C" {
        typedef void (*PFC)();    // pointer to "C" function
        void f(void(*)());        // takes pointer to "C" function
    }

    void f(void(*)());            // new overload of "f", taking
                                  // pointer to "C++" function

    void f(PFC);                  // redeclare extern "C" version
</PRE>

<P>
<B>Notes from 04/00 meeting:</B>
</P>

<P>The following changes were tentatively approved, but because they
do not completely implement the proposal above the issue is being kept
for the moment in "drafting" status.</P>

<P>
<B>Notes from 10/00 meeting:</B>
</P>

<P>After further discussion, the core language working group
determined that the more extensive proposal described above is
not needed and that the following changes are sufficient.</P>

<P>
<B>Proposed resolution (04/01):</B>
</P>

<OL>
<LI>
<P>Change the first sentence of 7.5&nbsp;



 <A HREF="dcl.html#dcl.link">dcl.link</A>
paragraph 1 from</P>

<BLOCKQUOTE>
All function types, function names, and variable names
have a language linkage.
</BLOCKQUOTE>

<P>to</P>

<BLOCKQUOTE>
All function types, function names with external
linkage, and variable names with external linkage have
a language linkage.
</BLOCKQUOTE>
</LI>

<LI>Change the following sentence of 7.5&nbsp;



 <A HREF="dcl.html#dcl.link">dcl.link</A>
paragraph 4:

<BLOCKQUOTE>
In a <I>linkage-specification</I>, the specified language
linkage applies to the function types of all function
declarators, function names, and variable names
introduced by the declaration(s).
</BLOCKQUOTE>

<P>to</P>

<BLOCKQUOTE>
In a <I>linkage-specification</I>, the specified language
linkage applies to the function types of all function
declarators, function names with external linkage, and
variable names with external linkage declared within
the <I>linkage-specification</I>.
</BLOCKQUOTE>
</LI>

<LI>
<P>Add at the end of the final example on 7.5&nbsp;



 <A HREF="dcl.html#dcl.link">dcl.link</A> paragraph 4:</P>

<PRE>
    extern "C" {
      static void f4();    // <I>the name of the function</I> f4 <I>has</I>
                           // <I>internal linkage (not C language</I>
                           // <I>linkage) and the function's type</I>
                           // <I>has C language linkage</I>
    }
    extern "C" void f5() {
      extern void f4();    // <I>Okay -- name linkage (internal)</I>
                           // <I>and function type linkage (C</I>
                           // <I>language linkage) gotten from</I>
                           // <I>previous declaration.</I>
    }
    extern void f4();      // <I>Okay -- name linkage (internal)</I>
                           // <I>and function type linkage (C</I>
                           // <I>language linkage) gotten from</I>
                           // <I>previous declaration.</I>
    void f6() {
      extern void f4();    // <I>Okay -- name linkage (internal)</I>
                           // <I>and function type linkage (C</I>
                           // <I>language linkage) gotten from</I>
                           // <I>previous declaration.</I>
    }
</PRE>
</LI>

<LI>
<P>Change 7.5&nbsp;



 <A HREF="dcl.html#dcl.link">dcl.link</A> paragraph 7 from</P>

<BLOCKQUOTE>
<P>Except for functions with internal linkage, a function
first declared in a <I>linkage-specification</I> behaves as a
function with external linkage.  [<I>Example:</I>
</P>

<PRE>
    extern "C" double f();
    static double f();     // <I>error</I>
</PRE>

<P>is ill-formed (7.1.1&nbsp;



 <A HREF="dcl.html#dcl.stc">dcl.stc</A>). ] The form of
<I>linkage-specification</I> that contains a braced-enclosed
<I>declaration-seq</I> does not affect whether the contained
declarations are definitions or not (3.1&nbsp;



 <A HREF="basic.html#basic.def">basic.def</A>); the
form of <I>linkage-specification</I> directly containing a
single declaration is treated as an <TT>extern</TT> specifier
(7.1.1&nbsp;



 <A HREF="dcl.html#dcl.stc">dcl.stc</A>) for the purpose of determining whether
the contained declaration is a definition.  [<I>Example:</I>
</P>

<PRE>
    extern "C" int i;      // <I>declaration</I>
    extern "C" {
	  int i;           // <I>definition</I>
    }
</PRE>

<P>&mdash;<I>end example</I>] A <I>linkage-specification</I> directly
containing a single declaration shall not specify a
storage class.  [<I>Example:</I>
</P>

<PRE>
    extern "C" static void f(); // <I>error</I>
</PRE>

<P>&mdash;<I>end example</I>]</P>
</BLOCKQUOTE>

<P>to</P>

<BLOCKQUOTE>
A declaration directly contained in a
<I>linkage-specification</I> is treated as if it contains the
<TT>extern</TT> specifier (7.1.1&nbsp;



 <A HREF="dcl.html#dcl.stc">dcl.stc</A>) for the purpose of
determining the linkage of the declared name and
whether it is a definition.  Such a declaration shall
not specify a storage class.  [<I>Example:</I>

<PRE>
    extern "C" double f();
    static double f();     // <I>error</I>
    extern "C" int i;      // <I>declaration</I>
    extern "C" {
	    int i;         // <I>definition</I>
    }
    extern "C" static void g(); // <I>error</I>
</PRE>

<P>&mdash;<I>end example</I>]</P>
</BLOCKQUOTE>
</LI>
</OL>
<BR>
<BR>
<HR>
<A NAME="29"></A>
<H4>29.
  
Linkage of locally declared functions
</H4>
<B>Section: </B>7.5&nbsp;



 <A HREF="dcl.html#dcl.link">dcl.link</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Ball
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>19 Mar 1998<BR>



<P>[Moved to DR at October 2002 meeting.  This was incorrectly
marked as having DR status between 4/01 and 4/02.  It was overlooked
when <A HREF="
     cwg_defects.html#4">issue 4</A> was moved to DR at the 4/01
meeting; this one should have been moved as well, because it's resolved
by the changes there.]</P>



<P>Consider the following:</P>
<PRE>
    extern "C" void foo()
    {
        extern void bar();
        bar();
    }
</PRE>
Does "bar()" have "C" language linkage?

<P>The ARM is explicit and says</P>
<BLOCKQUOTE>A linkage-specification for a function also applies to functions
and objects declared within it.</BLOCKQUOTE>
The DIS says
<BLOCKQUOTE>In a <I>linkage-specification</I>, the specified language linkage
applies to the function types of all function declarators, function names,
and variable names introduced by the declaration(s).</BLOCKQUOTE>
Is the body of a function definition part of the declaration?

<P>
<U>From Mike Miller:</U>
</P>

<P>Yes: from 7&nbsp;



 <A HREF="dcl.html#dcl.dcl">dcl.dcl</A>
 paragraph 1,</P>
<UL>
<I>declaration:</I>
<UL>
<I>function-definition</I>
</UL>
</UL>
and 8.4&nbsp;



 <A HREF="decl.html#dcl.fct.def">dcl.fct.def</A>
 paragraph 1:
<UL>
<I>function-definition:</I>
<UL>
<I>decl-specifier-seq<SUB>opt</SUB> declarator ctor-initializer<SUB>opt</SUB>&nbsp;function-body</I>
</UL>
</UL>
At least that's how I'd read it.

<P>
<U>From Dag Br&uuml;ck:</U>
</P>

<P>Consider the
following where extern "C" has been moved to a separate declaration:</P>
<PRE>
    extern "C" void foo();
    
    void foo() { extern void bar(); bar(); }
</PRE>
I think the ARM wording could possibly be interpreted such that bar() has
"C" linkage in my example, but not the DIS wording.

<P>As a side note, I have always wanted to think that placing extern "C"
on a function definition or a separate declaration would produce identical
programs.</P>

<P>
<B>Proposed Resolution (04/01):</B>
</P>

<P>See the proposed resolution for
<A HREF="
     cwg_defects.html#4">Core issue 4</A>, which covers this case.</P>

<P>The ODR should also be checked to see whether it addresses name and
type linkage.</P>
<BR>
<BR>
<HR>
<A NAME="160"></A>
<H4>160.
  
Missing <TT>std::</TT> qualification
</H4>
<B>Section: </B>8.2&nbsp;



 <A HREF="decl.html#dcl.ambig.res">dcl.ambig.res</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Al Stevens
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>23 Aug 1999<BR>



<P>[Moved to DR at 10/01 meeting.]</P>

<P>8.2&nbsp;



 <A HREF="decl.html#dcl.ambig.res">dcl.ambig.res</A>
 paragraph 3
shows an example that includes <TT>&lt;cstddef&gt;</TT> with no using
declarations or directives and refers to <TT>size_t</TT>
without the <TT>std::</TT>
qualification.</P>

<P>Many references to <TT>size_t</TT> throughout the document omit the
<TT>std::</TT>
namespace
qualification.</P>

<P>This is a typical case. The use of <TT>std::</TT>
is inconsistent throughout
the
document.</P>

<P>In addition, the use of exception specifications should be
examined for consistency.</P>

<P>(See also <A HREF="
     cwg_active.html#282">issue 282</A>.)</P>

<P>
<B>Proposed resolution:</B>
</P>

<P>In
1.9&nbsp;



 <A HREF="intro.html#intro.execution">intro.execution</A>
paragraph 9, replace all two instances of "<TT>sig_atomic_t</TT>"
by "<TT>std::sig_atomic_t</TT>".</P>


<P>In
3.1&nbsp;



 <A HREF="basic.html#basic.def">basic.def</A>
paragraph 4, replace all three instances of "<TT>string</TT>" by
"<TT>std::string</TT>" in the example and insert "<TT>#include
&lt;string&gt;</TT>" at the beginning of the example code.</P>


<P>In
3.6.1&nbsp;



 <A HREF="basic.html#basic.start.main">basic.start.main</A>
paragraph 4, replace</P>
<BLOCKQUOTE>
Calling the function
<BLOCKQUOTE>
<TT>void exit(int);</TT>
</BLOCKQUOTE>
declared in <TT>&lt;cstdlib&gt;</TT>...
</BLOCKQUOTE>
<P>by</P>
<BLOCKQUOTE>
Calling the function <TT>std::exit(int)</TT> declared in
<TT>&lt;cstdlib&gt;</TT>...
</BLOCKQUOTE>
<P>and also replace "<TT>exit</TT>" by "<TT>std::exit</TT>" in
the last sentence of that paragraph.</P>


<P>In
3.6.1&nbsp;



 <A HREF="basic.html#basic.start.main">basic.start.main</A>
first sentence of paragraph 5, replace "<TT>exit</TT>" by
"<TT>std::exit</TT>".</P>


<P>In
3.6.2&nbsp;



 <A HREF="basic.html#basic.start.init">basic.start.init</A>
paragraph 4, replace "<TT>terminate</TT>" by
"<TT>std::terminate</TT>".</P>


<P>In
3.6.3&nbsp;



 <A HREF="basic.html#basic.start.term">basic.start.term</A>
paragraph 1, replace "<TT>exit</TT>" by "<TT>std::exit</TT>"
(see also <A HREF="
     cwg_active.html#28">issue 28</A>).</P>


<P>In
3.6.3&nbsp;



 <A HREF="basic.html#basic.start.term">basic.start.term</A>
paragraph 3, replace all three instances of "<TT>atexit</TT>" by
"<TT>std::atexit</TT>" and both instances of "<TT>exit</TT>"
by "<TT>std::exit</TT>" (see also <A HREF="
     cwg_active.html#28">issue 28</A>).</P>


<P>In
3.6.3&nbsp;



 <A HREF="basic.html#basic.start.term">basic.start.term</A>
paragraph 4, replace</P>
<BLOCKQUOTE>
Calling the function
<BLOCKQUOTE>
<TT>void abort();</TT>
</BLOCKQUOTE>
declared in <TT>&lt;cstdlib&gt;</TT>...
</BLOCKQUOTE>
<P>by</P>
<BLOCKQUOTE>
Calling the function <TT>std::abort()</TT> declared in
<TT>&lt;cstdlib&gt;</TT>...</BLOCKQUOTE>
and "<TT>atexit</TT>" by "<TT>std::atexit</TT>" (see also
<A HREF="
     cwg_active.html#28">issue 28</A>).


<P>In
3.7.3.1&nbsp;



 <A HREF="basic.html#basic.stc.dynamic.allocation">basic.stc.dynamic.allocation</A>
paragraph 1 third sentence, replace "<TT>size_t</TT>" by
"<TT>std::size_t</TT>".</P>


<P>In
3.7.3.1&nbsp;



 <A HREF="basic.html#basic.stc.dynamic.allocation">basic.stc.dynamic.allocation</A>
paragraph 3, replace "<TT>new_handler</TT>" by
"<TT>std::new_handler</TT>". Furthermore, replace
"<TT>set_new_handler</TT>" by "<TT>std::set_new_handler</TT>"
in the note.</P>


<P>In
3.7.3.1&nbsp;



 <A HREF="basic.html#basic.stc.dynamic.allocation">basic.stc.dynamic.allocation</A>
paragraph 4, replace "<TT>type_info</TT>" by
"<TT>std::type_info</TT>" in the note.</P>


<P>In
3.7.3.2&nbsp;



 <A HREF="basic.html#basic.stc.dynamic.deallocation">basic.stc.dynamic.deallocation</A>
paragraph 3, replace all four instances of "<TT>size_t</TT>" by
"<TT>std::size_t</TT>".</P>


<P>In
3.8&nbsp;



 <A HREF="basic.html#basic.life">basic.life</A>
paragraph 5, replace "<TT>malloc</TT>" by
"<TT>std::malloc</TT>" in the example code and insert
"<TT>#include &lt;cstdlib&gt;</TT>" at the beginning of the example
code.</P>


<P>In
3.9&nbsp;



 <A HREF="basic.html#basic.types">basic.types</A>
paragraph 2, replace "<TT>memcpy</TT>" by
"<TT>std::memcpy</TT>" (the only instance in the footnote and both
instances in the example) and replace "<TT>memmove</TT>" by
"<TT>std::memmove</TT>" in the footnote (see also
<A HREF="
     cwg_defects.html#43">issue 43</A>).</P>


<P>In
3.9&nbsp;



 <A HREF="basic.html#basic.types">basic.types</A>
paragraph 3, replace "<TT>memcpy</TT>" by
"<TT>std::memcpy</TT>", once in the normative text and once in the
example (see also <A HREF="
     cwg_defects.html#43">issue 43</A>).</P>


<P>In
3.9.1&nbsp;



 <A HREF="basic.html#basic.fundamental">basic.fundamental</A>
paragraph 8 last sentence, replace "<TT>numeric_limits</TT>" by
"<TT>std::numeric_limits</TT>".</P>


<P>In
5.2.7&nbsp;



 <A HREF="expr.html#expr.dynamic.cast">expr.dynamic.cast</A>
paragraph 9 second sentence, replace "<TT>bad_cast</TT>" by
"<TT>std::bad_cast</TT>".</P>


<P>In
5.2.8&nbsp;



 <A HREF="expr.html#expr.typeid">expr.typeid</A>
paragraph 2, replace "<TT>type_info</TT>" by
"<TT>std::type_info</TT>" and "<TT>bad_typeid</TT>" by
"<TT>std::bad_typeid</TT>".</P>


<P>In
5.2.8&nbsp;



 <A HREF="expr.html#expr.typeid">expr.typeid</A>
paragraph 3, replace "<TT>type_info</TT>" by
"<TT>std::type_info</TT>".</P>


<P>In
5.2.8&nbsp;



 <A HREF="expr.html#expr.typeid">expr.typeid</A>
paragraph 4, replace both instances of "<TT>type_info</TT>" by
"<TT>std::type_info</TT>".</P>


<P>In
5.3.3&nbsp;



 <A HREF="expr.html#expr.sizeof">expr.sizeof</A>
paragraph 6, replace both instances of "<TT>size_t</TT>" by
"<TT>std::size_t</TT>".</P>


<P>In
5.3.4&nbsp;



 <A HREF="expr.html#expr.new">expr.new</A>
paragraph 11 last sentence, replace "<TT>size_t</TT>" by
"<TT>std::size_t</TT>".</P>


<P>In
5.7&nbsp;



 <A HREF="expr.html#expr.add">expr.add</A>
paragraph 6, replace both instances of "<TT>ptrdiff_t</TT>" by
"<TT>std::ptrdiff_t</TT>".</P>


<P>In
5.7&nbsp;



 <A HREF="expr.html#expr.add">expr.add</A>
paragraph 8, replace "<TT>ptrdiff_t</TT>" by
"<TT>std::ptrdiff_t</TT>".</P>


<P>In
6.6&nbsp;



 <A HREF="stmt.html#stmt.jump">stmt.jump</A>
paragraph 2, replace "<TT>exit</TT>" by "<TT>std::exit</TT>"
and "<TT>abort</TT>" by "<TT>std::abort</TT>" in the note.</P>


<P>In
8.2&nbsp;



 <A HREF="decl.html#dcl.ambig.res">dcl.ambig.res</A>
paragraph 3, replace "<TT>size_t</TT>" by
"<TT>std::size_t</TT>" in the example.</P>


<P>In
8.4&nbsp;



 <A HREF="decl.html#dcl.fct.def">dcl.fct.def</A>
paragraph 5, replace "<TT>printf</TT>" by
"<TT>std::printf</TT>" in the note.</P>


<P>In
12.4&nbsp;



 <A HREF="special.html#class.dtor">class.dtor</A>
paragraph 13, replace "<TT>size_t</TT>" by
"<TT>std::size_t</TT>" in the example.</P>


<P>In
12.5&nbsp;



 <A HREF="special.html#class.free">class.free</A>
paragraph 2, replace all four instances of "<TT>size_t</TT>" by
"<TT>std::size_t</TT>" in the example.</P>


<P>In
12.5&nbsp;



 <A HREF="special.html#class.free">class.free</A>
paragraph 6, replace both instances of "<TT>size_t</TT>" by
"<TT>std::size_t</TT>" in the example.</P>


<P>In
12.5&nbsp;



 <A HREF="special.html#class.free">class.free</A>
paragraph 7, replace all four instances of "<TT>size_t</TT>" by
"<TT>std::size_t</TT>" in the two examples.</P>


<P>In
12.7&nbsp;



 <A HREF="special.html#class.cdtor">class.cdtor</A>
paragraph 4, replace "<TT>type_info</TT>" by
"<TT>std::type_info</TT>".</P>


<P>In
13.6&nbsp;



 <A HREF="over.html#over.built">over.built</A>
paragraph 13, replace all five instances of "<TT>ptrdiff_t</TT>"
by "<TT>std::ptrdiff_t</TT>".</P>


<P>In
13.6&nbsp;



 <A HREF="over.html#over.built">over.built</A>
paragraph 14, replace "<TT>ptrdiff_t</TT>" by
"<TT>std::ptrdiff_t</TT>".</P>


<P>In
13.6&nbsp;



 <A HREF="over.html#over.built">over.built</A>
paragraph 21, replace both instances of "<TT>ptrdiff_t</TT>" by
"<TT>std::ptrdiff_t</TT>".</P>


<P>In
14.2&nbsp;



 <A HREF="template.html#temp.names">temp.names</A>
paragraph 4, replace both instances of "<TT>size_t</TT>" by
"<TT>std::size_t</TT>" in the example.  (The example is quoted in
<A HREF="
     cwg_active.html#96">issue 96</A>.)</P>


<P>In
14.3&nbsp;



 <A HREF="template.html#temp.arg">temp.arg</A>
paragraph 1, replace "<TT>complex</TT>" by
"<TT>std::complex</TT>", once in the example code and once in the
comment.</P>


<P>In
14.7.3&nbsp;



 <A HREF="template.html#temp.expl.spec">temp.expl.spec</A>
paragraph 8, <A HREF="
     cwg_defects.html#24">issue 24</A>
has already corrected the example.</P>


<P>In
15.1&nbsp;



 <A HREF="except.html#except.throw">except.throw</A>
paragraph 6, replace "<TT>uncaught_exception</TT>" by
"<TT>std::uncaught_exception</TT>".</P>


<P>In
15.1&nbsp;



 <A HREF="except.html#except.throw">except.throw</A>
paragraph 7, replace "<TT>terminate</TT>" by
"<TT>std::terminate</TT>" and both instances of
"<TT>unexpected</TT>" by "<TT>std::unexpected</TT>".</P>


<P>In
15.1&nbsp;



 <A HREF="except.html#except.throw">except.throw</A>
paragraph 8, replace "<TT>terminate</TT>" by
"<TT>std::terminate</TT>".</P>


<P>In
15.2&nbsp;



 <A HREF="except.html#except.ctor">except.ctor</A>
paragraph 3, replace "<TT>terminate</TT>" by
"<TT>std::terminate</TT>".</P>


<P>In
15.3&nbsp;



 <A HREF="except.html#except.handle">except.handle</A>
paragraph 9, replace "<TT>terminate</TT>" by
"<TT>std::terminate</TT>".</P>


<P>In
15.4&nbsp;



 <A HREF="except.html#except.spec">except.spec</A>
paragraph 8, replace "<TT>unexpected</TT>" by
"<TT>std::unexpected</TT>".</P>


<P>In
15.4&nbsp;



 <A HREF="except.html#except.spec">except.spec</A>
paragraph 9, replace "<TT>unexpected</TT>" by
"<TT>std::unexpected</TT>" and "<TT>terminate</TT>" by
"<TT>std::terminate</TT>".</P>


<P>In
15.5&nbsp;



 <A HREF="except.html#except.special">except.special</A>
paragraph 1, replace "<TT>terminate</TT>" by
"<TT>std::terminate</TT>" and "<TT>unexpected</TT>" by
"<TT>std::unexpected</TT>".</P>


<P>In the heading of
15.5.1&nbsp;



 <A HREF="except.html#except.terminate">except.terminate</A>,
replace "<TT>terminate</TT>" by "<TT>std::terminate</TT>".</P>


<P>In
15.5.1&nbsp;



 <A HREF="except.html#except.terminate">except.terminate</A>
paragraph 1, footnote in the first bullet, replace
"<TT>terminate</TT>" by "<TT>std::terminate</TT>".  In the
same paragraph, fifth bullet, replace "<TT>atexit</TT>" by
"<TT>std::atexit</TT>".  In the same paragraph, last bullet,
replace "<TT>unexpected_handler</TT>" by
"<TT>std::unexpected_handler</TT>".</P>


<P>In
15.5.1&nbsp;



 <A HREF="except.html#except.terminate">except.terminate</A>
paragraph 2, replace</P>
<BLOCKQUOTE>
In such cases,
<BLOCKQUOTE>
<TT>void terminate();</TT>
</BLOCKQUOTE>
is called...
</BLOCKQUOTE>
<P>by</P>
<BLOCKQUOTE>
In such cases, <TT>std::terminate()</TT> is called...
</BLOCKQUOTE>
<P>and replace all three instances of "<TT>terminate</TT>" by
"<TT>std::terminate</TT>".</P>


<P>In the heading of
15.5.2&nbsp;



 <A HREF="except.html#except.unexpected">except.unexpected</A>,
replace "<TT>unexpected</TT>" by "<TT>std::unexpected</TT>".</P>


<P>In
15.5.2&nbsp;



 <A HREF="except.html#except.unexpected">except.unexpected</A>
paragraph 1, replace </P>
<BLOCKQUOTE>
...the function
<BLOCKQUOTE>
<TT>void unexpected();</TT>
</BLOCKQUOTE>
is called...
</BLOCKQUOTE>
<P>by</P>
<BLOCKQUOTE>
...the function <TT>std::unexpected()</TT> is called...
</BLOCKQUOTE>.


<P>In
15.5.2&nbsp;



 <A HREF="except.html#except.unexpected">except.unexpected</A>
paragraph 2, replace "<TT>unexpected</TT>" by
"<TT>std::unexpected</TT>" and "<TT>terminate</TT>" by
"<TT>std::terminate</TT>".</P>


<P>In
15.5.2&nbsp;



 <A HREF="except.html#except.unexpected">except.unexpected</A>
paragraph 3, replace "<TT>unexpected</TT>" by
"<TT>std::unexpected</TT>".</P>


<P>In the heading of
15.5.3&nbsp;



 <A HREF="except.html#except.uncaught">except.uncaught</A>,
replace "<TT>uncaught_exception</TT>" by
"<TT>std::uncaught_exception</TT>".</P>


<P>In 
15.5.3&nbsp;



 <A HREF="except.html#except.uncaught">except.uncaught</A>
paragraph 1, replace</P>
<BLOCKQUOTE>
The function
<BLOCKQUOTE>
<TT>bool uncaught_exception()</TT>
</BLOCKQUOTE>
returns <TT>true</TT>...
</BLOCKQUOTE>
<P>by</P>
<BLOCKQUOTE>
The function <TT>std::uncaught_exception()</TT> returns <TT>true</TT>...
</BLOCKQUOTE>.
<P>In the last sentence of the same paragraph, replace
"<TT>uncaught_exception</TT>" by
"<TT>std::uncaught_exception</TT>".</P>

<BR>
<BR>
<HR>
<A NAME="112"></A>
<H4>112.
  
Array types and cv-qualifiers
</H4>
<B>Section: </B>8.3.4&nbsp;



 <A HREF="decl.html#dcl.array">dcl.array</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Clamage
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>4 May 1999<BR>



<P>[Moved to DR at 10/01 meeting.]</P>



<P>
<U>Steve Clamage:</U>
Section 8.3.4&nbsp;



 <A HREF="decl.html#dcl.array">dcl.array</A>
 paragraph 1
reads in part as follows:</P>

<BLOCKQUOTE>
Any type of the form "<I>cv-qualifier-seq</I> array of <TT>N T</TT>"
is adjusted to
"array of <TT>N</TT> <I>cv-qualifier-seq</I> <TT>T</TT>,"
and similarly for "array of unknown
bound of <TT>T</TT>." [<I>Example:</I>
<PRE>
    typedef int A[5], AA[2][3];
    typedef const A CA;     // <I>type is "array of 5 const int"</I>
    typedef const AA CAA;   // <I>type is "array of 2 array of 3 const int"</I>
</PRE>
&mdash;<I>end example</I>]
[<I>Note:</I> an "array of <TT>N</TT> <I>cv-qualifier-seq</I> <TT>T</TT>"
has cv-qualified type; such
an array has internal linkage unless explicitly declared <TT>extern</TT>
(7.1.5.1&nbsp;



 <A HREF="dcl.html#dcl.type.cv">dcl.type.cv</A>
)
and must be initialized as specified in
8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A>
. ]
</BLOCKQUOTE>

The Note appears to contradict the sentence that precedes it. 

<P>
<U>Mike Miller:</U>
I disagree; all it says is that whether the qualification on
the element type is direct ("<TT>const int x[5]</TT>") or indirect
("<TT>const A CA</TT>"), the array itself is qualified in the same way
the elements are.</P>

<P>
<U>Steve Clamage:</U> In addition, section
3.9.3&nbsp;



 <A HREF="basic.html#basic.type.qualifier">basic.type.qualifier</A>
 paragraph 2 says:</P>

<BLOCKQUOTE>
A compound type (3.9.2&nbsp;



 <A HREF="basic.html#basic.compound">basic.compound</A>
)
is not cv-qualified by the cv-qualifiers (if
any) of the types from which it is compounded.  Any cv-qualifiers
applied to an array type affect the array element type, not the
array type (8.3.4&nbsp;



 <A HREF="decl.html#dcl.array">dcl.array</A>
)."
</BLOCKQUOTE>

The Note appears to contradict that section as well.

<P>
<U>Mike Miller:</U>
Yes, but consider the last two sentences of
3.9.3&nbsp;



 <A HREF="basic.html#basic.type.qualifier">basic.type.qualifier</A>
 paragraph 5:</P>
<BLOCKQUOTE>
Cv-qualifiers applied to an array type attach to the
underlying element type, so the notation "<I>cv</I> <TT>T</TT>,"
where <TT>T</TT> is
an array type, refers to an array whose elements are
so-qualified.  Such array types can be said to be more (or
less) cv-qualified than other types based on the cv-qualification
of the underlying element types.
</BLOCKQUOTE>

I think this says essentially the same thing as
8.3.4&nbsp;



 <A HREF="decl.html#dcl.array">dcl.array</A>
 paragraph 1 and
its note: the qualification of an array is (bidirectionally)
equivalent to the qualification of its members.

<P>
<U>Mike Ball:</U>
I find this a very far reach.  The text in
8.3.4&nbsp;



 <A HREF="decl.html#dcl.array">dcl.array</A>
 is essentially that which
is in the C standard (and is a change from early versions of C++).
I don't see any justification at all for the bidirectional equivalence.
It seems to me that
the note is left over from the earlier version of the language.</P>

<P>
<U>Steve Clamage:</U> Finally, the Note seems to say that the declaration</P>
<PRE>
    volatile char greet[6] = "Hello";
</PRE>
gives "greet" internal linkage, which makes no sense.

<P>Have I missed something, or should that Note be entirely removed?</P>

<P>
<U>Mike Miller:</U>
At least the wording in the note
should be repaired not to indicate that volatile-qualification
gives an array internal linkage.  Also, depending on how the
discussion goes, either the wording in
3.9.3&nbsp;



 <A HREF="basic.html#basic.type.qualifier">basic.type.qualifier</A>
 paragraph 2
or in paragraph 5 needs
to be amended to be consistent regarding whether an array type
is considered qualified by the qualification of its element
type.</P>

<P>
<U>Steve Adamczyk</U> pointed out that
the current state of affairs resulted from the need to handle
reference binding consistently.  The wording is intended to define
the question, "Is an array type cv-qualified?" as being equivalent
to the question, "Is the element type of the array cv-qualified?"</P>

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>Replace the portion of the note in 8.3.4&nbsp;



 <A HREF="decl.html#dcl.array">dcl.array</A>
paragraph 1 reading</P>

<BLOCKQUOTE>

such an array has internal linkage unless explicitly declared
<TT>extern</TT> (7.1.5.1&nbsp;



 <A HREF="dcl.html#dcl.type.cv">dcl.type.cv</A>) and must be
initialized as specified in 8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A>.

</BLOCKQUOTE>

<P>with</P>

<BLOCKQUOTE>

see 3.9.3&nbsp;



 <A HREF="basic.html#basic.type.qualifier">basic.type.qualifier</A>.

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="140"></A>
<H4>140.
  
Agreement of parameter declarations
</H4>
<B>Section: </B>8.3.5&nbsp;



 <A HREF="decl.html#dcl.fct">dcl.fct</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Clamage
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>15 Jul 1999<BR>



<P>[Moved to DR at 10/01 meeting.]</P>



<P>8.3.5&nbsp;



 <A HREF="decl.html#dcl.fct">dcl.fct</A>
 paragraph 3 says,</P>

<BLOCKQUOTE>
All declarations for a function with a given parameter list shall
agree exactly both in the type of the value returned and in the
number and type of parameters.
</BLOCKQUOTE>

It is not clear what this requirement means with respect to a pair
of declarations like the following:

<PRE>
    int f(const int);
    int f(int x) { ... }
</PRE>

Do they violate this requirement?  Is <TT>x const</TT> in the body of
the function declaration?

<P>
<U>Tom Plum</U>:
I think the FDIS quotation means that the pair of decls are valid.
But it doesn't clearly answer whether
<TT>x</TT> is <TT>const</TT> inside the function definition.
As to intent, I <I>know</I> the intent was that if the function
definition wants to specify that <TT>x</TT> is <TT>const</TT>,
the <TT>const</TT> must appear specifically in the defining
decl, not just on some decl elsewhere.
But I can't prove that intent from the drafted words.</P>

<P>
<U>Mike Miller</U>:
I think the intent was something along the
following lines:</P>

<BLOCKQUOTE>
Two function declarations denote the same entity if
the names are the same and the function signatures
are the same.  (Two function declarations with C
language linkage denote the same entity if the names
are the same.)  All declarations of a given function
shall agree exactly both in the type of the value
returned and in the number and type of parameters;
the presence or absence of the ellipsis is considered
part of the signature.
</BLOCKQUOTE>

(See 3.5&nbsp;



 <A HREF="basic.html#basic.link">basic.link</A>
 paragraph 9.
That paragraph talks about names in different
scopes and says that function references are the same if the
"types are identical for purposes of overloading," i.e., the
signatures are the same.  See also
7.5&nbsp;



 <A HREF="dcl.html#dcl.link">dcl.link</A>
 paragraph 6
regarding C language
linkage, where only the name is required to be the same for
declarations in different namespaces to denote the same
function.)

<P>According to this paragraph, the type of a parameter is
determined by considering its <I>decl-specifier-seq</I> and
<I>declarator</I>
and then applying the array-to-pointer and function-to-pointer
adjustments.  The <I>cv-qualifier</I> and storage class adjustments
are performed for the function type but not for the parameter
types.</P>

<P>If my interpretation of the intent of the second sentence of
the paragraph is correct, the two declarations in the example
violate that restriction &mdash; the parameter types are not the
same, even though the function types are.  Since there's no
dispensation mentioned for "no diagnostic required," an
implementation presumably must issue a diagnostic in this
case.  (I think "no diagnostic required" should be stated if
the declarations occur in different translation units &mdash;
unless there's a blanket statement to that effect that I have
forgotten?)</P>

<P>(I'd also note in passing that, if my interpretation is
correct,</P>

<PRE>
    void f(int);
    void f(register int) { }
</PRE>

is also an invalid pair of declarations.)



<P>
<B>Proposed resolution (10/00):</B>
</P>

<OL>
<LI>
<P>In 1.3.10&nbsp;



 <A HREF="intro.html#defns.signature">defns.signature</A>, change
"the types of its parameters"
to
"its parameter-type-list (8.3.5&nbsp;



 <A HREF="decl.html#dcl.fct">dcl.fct</A>)".
</P>
</LI>

<LI>
<P>In the third bullet of 3.5&nbsp;



 <A HREF="basic.html#basic.link">basic.link</A> paragraph 9
change
"the function types are identical for the purposes of overloading"
to
"the parameter-type-lists of the functions (8.3.5&nbsp;



 <A HREF="decl.html#dcl.fct">dcl.fct</A>) are identical."
</P>
</LI>

<LI>
<P>In the sub-bullets of the third bullet of
5.2.5&nbsp;



 <A HREF="expr.html#expr.ref">expr.ref</A> paragraph 4, change all four occurrences
of
"function of (parameter type list)"
to
"function of parameter-type-list."
</P>
</LI>

<LI>
<P>In 8.3.5&nbsp;



 <A HREF="decl.html#dcl.fct">dcl.fct</A> paragraph 3, change

<BLOCKQUOTE>
All declarations for a function with a given parameter list shall agree
exactly both in the type of the value returned and in the number and
type of parameters; the presence or absence of the ellipsis is
considered part of the function type.
</BLOCKQUOTE>

to

<BLOCKQUOTE>
All declarations for a function shall
agree exactly in both the return type and the
parameter-type-list.
</BLOCKQUOTE>
</P>
</LI>

<LI>
<P>In 8.3.5&nbsp;



 <A HREF="decl.html#dcl.fct">dcl.fct</A> paragraph 3, change

<BLOCKQUOTE>
The resulting list of transformed parameter types is the function's
<I>parameter type list</I>.
</BLOCKQUOTE>

to

<BLOCKQUOTE>
The resulting list of transformed parameter types and the presence or
absence of the ellipsis is the function's <I>parameter-type-list</I>.
</BLOCKQUOTE>
</P>
</LI>

<LI>
<P>In 8.3.5&nbsp;



 <A HREF="decl.html#dcl.fct">dcl.fct</A> paragraph 4, change
"the parameter type list"
to
"the parameter-type-list."
</P>
</LI>

<LI>
<P>In the second bullet of 13.1&nbsp;



 <A HREF="over.html#over.load">over.load</A> paragraph 2,
change all occurrences of "parameter types" to
"parameter-type-list."
</P>
</LI>

<LI>
<P>In 13.3&nbsp;



 <A HREF="over.html#over.match">over.match</A> paragraph 1, change "the types of
the parameters" to "the parameter-type-list."
</P>
</LI>

<LI>
<P>In the last sub-bullet of the third bullet of
13.3.1.2&nbsp;



 <A HREF="over.html#over.match.oper">over.match.oper</A> paragraph 3, change "parameter type
list" to "parameter-type-list."
</P>
</LI>

</OL>
<P>
<B>Note, 7 Sep 2001:</B>
</P>
<P>Editorial changes while putting in <A HREF="
     cwg_defects.html#147">issue 147</A>
brought up the fact that injected-class-name is not a syntax term and
therefore perhaps shouldn't be written with hyphens. The same can be said of
parameter-type-list.

</P>
<BR>
<BR>
<HR>
<A NAME="262"></A>
<H4>262.
  
Default arguments and ellipsis
</H4>
<B>Section: </B>8.3.5&nbsp;



 <A HREF="decl.html#dcl.fct">dcl.fct</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Jamie Schmeiser
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>13 Nov 2000<BR>


<P>[Voted into WP at April 2003 meeting.]</P>



<P>The interaction of default arguments and ellipsis is not clearly
spelled out in the current wording of the Standard.
8.3.6&nbsp;



 <A HREF="decl.html#dcl.fct.default">dcl.fct.default</A> paragraph 4 says,</P>

<BLOCKQUOTE>

In a given function declaration, all parameters subsequent to a
parameter with a default argument shall have default arguments
supplied in this or previous declarations.

</BLOCKQUOTE>

<P>Strictly speaking, ellipsis isn't a parameter, but this could
be clearer.  Also, in 8.3.5&nbsp;



 <A HREF="decl.html#dcl.fct">dcl.fct</A> paragraph 2,</P>

<BLOCKQUOTE>

If the <I>parameter-declaration-clause</I> terminates with an
ellipsis, the number of arguments shall be equal to or greater than
the number of parameters specified.

</BLOCKQUOTE>

<P>This could be interpreted to refer to the number of arguments
after the addition of default arguments to the argument list given
in the call expression, but again it could be clearer.</P>

<P>
<B>Notes from 04/01 meeting:</B>
</P>

<P>The consensus opinion was that an ellipsis is not a parameter
and that default arguments should be permitted preceding an
ellipsis.</P>

<P>
<B>Proposed Resolution (4/02):</B>
</P>

<P>Change the following sentence in 8.3.5&nbsp;



 <A HREF="decl.html#dcl.fct">dcl.fct</A> paragraph 2
from</P>
<BLOCKQUOTE>
If the <I>parameter-declaration-clause</I> terminates with an ellipsis, the
number of arguments shall be equal to or greater than the number of
parameters specified.
</BLOCKQUOTE>
<P>to</P>
<BLOCKQUOTE>
If the <I>parameter-declaration-clause</I> terminates with an ellipsis, the
number of arguments shall be equal to or greater than the number of
parameters that do not have a default argument.
</BLOCKQUOTE>

<P>As noted in the defect, section 8.3.6&nbsp;



 <A HREF="decl.html#dcl.fct.default">dcl.fct.default</A>
is correct but could be clearer.</P>

<P>In 8.3.6&nbsp;



 <A HREF="decl.html#dcl.fct.default">dcl.fct.default</A>, add the following as the first line
of the example in paragraph 4.</P>
<PRE>
  void g(int = 0, ...);  // okay, ellipsis is not a parameter so it can follow 
                         // a parameter with a default argument
</PRE>

<BR>
<BR>
<HR>
<A NAME="295"></A>
<H4>295.
  
cv-qualifiers on function types
</H4>
<B>Section: </B>8.3.5&nbsp;



 <A HREF="decl.html#dcl.fct">dcl.fct</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Nathan Sidwell
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>29 Jun 2001<BR>


<P>[Moved to DR at October 2002 meeting.]</P>

<P>This concerns the inconsistent treatment of cv qualifiers on
reference types and function types. The problem originated with
GCC bug report c++/2810. The bug report is available at
<A HREF="http://gcc.gnu.org/cgi-bin/gnatsweb.pl?cmd=view&amp;pr=2810&amp;database=gcc">
http://gcc.gnu.org/cgi-bin/gnatsweb.pl?cmd=view&amp;pr=2810&amp;database=gcc
</A>
</P>

<P>8.3.2&nbsp;



 <A HREF="decl.html#dcl.ref">dcl.ref</A> describes references. Of interest is
the statement (my emphasis)</P>
<BLOCKQUOTE>
Cv-qualified references are ill-formed <B>except</B> when
the cv-qualifiers are introduced through the use of a typedef
or of a template type argument, in which case the cv-qualifiers
are ignored.
</BLOCKQUOTE>
<P>Though it is strange to ignore 'volatile' here, that is not the point
of this defect report. 8.3.5&nbsp;



 <A HREF="decl.html#dcl.fct">dcl.fct</A> describes function types.
Paragraph 4 states,</P>
<BLOCKQUOTE>
In fact, if at any time in the determination of a type a
cv-qualified function type is formed, the program is ill-formed.
</BLOCKQUOTE>
<P>No allowance for typedefs or template type parameters is
made here, which is inconsistent with the equivalent reference case.</P>

<P>The GCC bug report was template code which attempted to do,</P>
<PRE>
    template &lt;typename T&gt; void foo (T const &amp;);
    void baz ();
    ...
    foo (baz);
</PRE>

<P>in the instantiation of foo, <TT>T</TT> is `<TT>void ()</TT>' and an attempt
is made to const qualify that, which is ill-formed. This is a surprise.</P>

<P>
<B>Suggested resolution:</B>
</P>

<P>Replace the quoted sentence from paragraph 4 in
8.3.5&nbsp;



 <A HREF="decl.html#dcl.fct">dcl.fct</A> with</P>
<BLOCKQUOTE>
cv-qualified functions are ill-formed, except when the
cv-qualifiers are introduced through the use of a typedef or of
a template type argument, in which case the cv-qualifiers are
ignored.
</BLOCKQUOTE>
<P>Adjust the example following to reflect this.</P>

<P>
<B>Proposed resolution (10/01):</B>
</P>

<P>In 8.3.5&nbsp;



 <A HREF="decl.html#dcl.fct">dcl.fct</A> paragraph 4, replace
<BLOCKQUOTE>
The effect of a <I>cv-qualifier-seq</I> in a function declarator is
not the same as adding cv-qualification on top of the function type,
i.e., it does not create a cv-qualified function type.  In fact, if at
any time in the determination of a type a cv-qualified function type
is formed, the program is ill-formed. [<I>Example:
</I>
<PRE>
  typedef void F();
  struct S {
    const F f;          // ill-formed
  };
</PRE>
<I>-- end example</I>]
</BLOCKQUOTE>
by
<BLOCKQUOTE>
The effect of a <I>cv-qualifier-seq</I> in a function declarator is
not the same as adding cv-qualification on top of the function type.
In the latter case, the cv-qualifiers are ignored.  [<I>Example:
</I>
<PRE>
  typedef void F();
  struct S {
    const F f;          // ok; equivalent to void f();
  };
</PRE>
<I>-- end example</I>]
</BLOCKQUOTE>
</P>

<P>Strike the last bulleted item in 14.8.2&nbsp;



 <A HREF="template.html#temp.deduct">temp.deduct</A>
paragraph 2, which reads
<BLOCKQUOTE>
Attempting to create a cv-qualified function type.
</BLOCKQUOTE>
</P>

<P>
<U>Nathan Sidwell</U> comments (18 Dec 2001
):
The proposed resolution simply states attempts to add cv qualification
on top of a function type are ignored.  There is no mention of whether
the function type was introduced via a typedef or template type parameter.
This would appear to allow
<PRE>
  void (const *fptr) ();
</PRE>
but, that is not permitted by the grammar.  This is inconsistent
with the wording of adding cv qualifiers to a reference type, which does
mention typedefs and template parameters, even though
<PRE>
  int &amp;const ref;
</PRE>
is also not allowed by the grammar.</P>

<P>Is this difference intentional? It seems needlessly confusing.</P>

<P>
<B>Notes from 4/02 meeting:</B>
</P>

<P>Yes, the difference is intentional.  There is no way to add cv-qualifiers
other than those cases.</P>

<P>
<B>Notes from April 2003 meeting:</B>
</P>

<P>Nathan Sidwell pointed out that some libraries use the inability to
add const to a type T as a way of testing that T is a function
type.  He will get back to us if he has a proposal for a change.</P>

<BR>
<BR>
<HR>
<A NAME="136"></A>
<H4>136.
  
Default arguments and friend declarations
</H4>
<B>Section: </B>8.3.6&nbsp;



 <A HREF="decl.html#dcl.fct.default">dcl.fct.default</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Daveed Vandevoorde
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>9 July 1999<BR>



<P>[Moved to DR at 10/01 meeting.]</P>



<P>8.3.6&nbsp;



 <A HREF="decl.html#dcl.fct.default">dcl.fct.default</A>
 paragraph 4 says,</P>

<BLOCKQUOTE>
For non-template functions, default arguments can be added in later
declarations of a function in the same scope.  Declarations in
different scopes have completely distinct sets of default arguments.
That is, declarations in inner scopes do not acquire default arguments
from declarations in outer scopes, and vice versa.
</BLOCKQUOTE>

It is unclear how this wording applies to friend function declarations.
For example,

<PRE>
    void f(int, int, int=0);             // #1
    class C {
        friend void f(int, int=0, int);  // #2
    };
    void f(int=0, int, int);             // #3
</PRE>

Does the declaration at #2 acquire the default argument from #1, and
does the one at #3 acquire the default arguments from #2?

<P>There are several related questions involved with this issue:</P>

<OL>
<LI>Is the friend
declaration in the scope of class C or in the surrounding namespace
scope?

<P>
<U>Mike Miller</U>:
8.3.6&nbsp;



 <A HREF="decl.html#dcl.fct.default">dcl.fct.default</A>
 paragraph 4
is speaking about the lexical location of the
declaration...
The friend declaration occurs in a different declarative region
from the declaration at #1, so I would read [this paragraph] as saying that it
starts out with a clean slate of default arguments.</P>

<P>
<U>Bill Gibbons</U>:
Yes.  It occurs in a different region, although it declares a name
in the same region (i.e. a redeclaration).  This is the same as with
local externs and is intended to work the same way.  We decided that
local extern declarations cannot add (beyond the enclosing block) new
default arguments, and the same should apply to friend declarations.</P>

<P>
<U>John Spicer</U>:
The question is whether [this paragraph]
does (or should) mean declarations that appear in the same lexical
scope or declarations that declare names in the same scope.  In my opinion,
it really needs to be the latter.  It seems somewhat paradoxical to say
that a friend declaration declares a function in namespace scope yet the
declaration in the class still has its own attributes.  To make that work
I think you'd have to make friends more like block externs that really do
introduce a name into the scope in which the declaration is contained.</P>
</LI>

<LI>Should default arguments be permitted in friend function
declarations, and what effect should they have?

<P>
<U>Bill Gibbons</U>:
In the absence of a declaration visible in class scope to which
they could be attached, default arguments on friend declarations
do not make sense.
[They should be] ill-formed, to prevent surprises.</P>

<P>
<U>John Spicer</U>:
It is important that
the following case work correctly:</P>

<PRE>
        class X {
                friend void f(X x, int i = 1){}
        };

        int main()
        {
                X x;
                f(x);
        }
</PRE>

<P>In other words, a function first declared in a friend declaration must be
permitted to have default arguments and those default arguments must be
usable when the function is found by argument dependent lookup.  The reason
that this is important is that it is common practice to <I>define</I> functions
in friend declarations in templates, and that definition is the only place
where the default arguments can be specified.</P>
</LI>

<LI>What restrictions should be placed on default argument usage with
friend declarations?

<P>
<U>John Spicer</U>:
We want to avoid instantiation side effects.  IMO, the way to do this
would be to prohibit a friend declaration from providing default arguments
if a declaration of that function is already visible.
Once a function has had a default specified in a friend
declaration it should not be possible to add defaults in another declaration
be it a friend or normal declaration.</P>

<P>
<U>Mike Miller</U>:
The position that seems most reasonable to me is to
allow default arguments in friend declarations to be used in
Koenig lookup, but to say that they are
completely unrelated to default arguments in declarations in
the surrounding scope; and to forbid use of a default argument
in a call if more than one declaration in the overload set has
such a default, as in the proposed resolution for
<A HREF="
     cwg_defects.html#1">issue 1</A>.</P>
</LI>

</OL>

(See also issues
<A HREF="
     cwg_defects.html#21">21</A>,
<A HREF="
     cwg_closed.html#95">95</A>,
<A HREF="
     cwg_active.html#138">138</A>,
<A HREF="
     cwg_defects.html#139">139</A>,
<A HREF="
     cwg_defects.html#143">143</A>,
<A HREF="
     cwg_closed.html#165">165</A>, and
<A HREF="
     cwg_defects.html#166">166</A>.)

<P>
<B>Notes from 10/99 meeting:</B>
</P>

<P>Four possible outcomes were identified:</P>

<OL>

<LI>If a friend declaration declares a default parameter, allow no
other declarations of that function in the translation unit.</LI>

<LI>Same as preceding, but only allow the friend declaration if it is
also a definition.</LI>

<LI>Disallow default arguments in friend declarations.</LI>

<LI>Treat the default arguments in each friend declaration as a
distinct set, causing an error if the call would be ambiguous.</LI>

</OL>

<P>The core group eliminated the first and fourth options from
consideration, but split fairly evenly between the remaining two.</P>

<P>A straw poll of the full committee yielded the following results
(given as number favoring/could live with/"over my dead body"):</P>

<OL>

<LI>0/14/5</LI>

<LI>8/13/5</LI>

<LI>11/7/14</LI>

<LI>7/10/9</LI>

</OL>

<P>Additional discussion is recorded in the "Record of Discussion" for
the meeting, J16/99-0036 = WG21 N1212.  See also paper
J16/00-0040 = WG21 N1263.</P>

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>In 8.3.6&nbsp;



 <A HREF="decl.html#dcl.fct.default">dcl.fct.default</A>, add following paragraph 4:</P>

<BLOCKQUOTE>

If a friend declaration specifies a default argument expression,
that declaration must be a definition and shall be the only declaration
of the function or function template in the translation unit.

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="5"></A>
<H4>5.
  
CV-qualifiers and type conversions
</H4>
<B>Section: </B>8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Josee Lajoie
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>unknown<BR>



<P>[Moved to DR at 4/01 meeting.]</P>



<P>The description of copy-initialization in 8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A>
 paragraph 14 says:</P>
<UL>
<LI>
If the destination type is a (possibly cv-qualified) class type:

<BR>&nbsp;...</LI>
<LI>
Otherwise (i.e. for the remaining copy-initialization cases), user-defined
conversion sequences that can convert from the source type to the destination
type or (when a conversion function is used) to a derived class thereof
are enumerated ... if the function is a constructor, the call initializes
a temporary of the destination type. ...
</LI>
</UL>
Should "destination type" in this last bullet refer to "cv-unqualified
destination type" to make it clear that the destination type excludes any
cv-qualifiers? This would make it clearer that the following example is
well-formed:
<PRE>
     struct A {
       A(A&amp;);
     };
     struct B : A { };
     
     struct C {
       operator B&amp;();
     };
     
     C c;
     const A a = c; // allowed?
</PRE>
<P>The temporary created with the conversion function is an lvalue of type
<TT>B</TT>. If the temporary must have the cv-qualifiers of the destination
type (i.e. const) then the copy-constructor for <TT>A</TT> cannot be called
to create the object of type <TT>A</TT> from the lvalue of type <TT>const
B</TT>. If the temporary has the cv-qualifiers of the result type of the
conversion function, then the copy-constructor for <TT>A</TT> can be called
to create the object of type <TT>A</TT> from the lvalue of type <TT>const
B</TT>. This last outcome seems more appropriate.</P>

<P>
<U>Steve Adamczyk</U>: </P>
<P>Because of late changes to this area, the
relevant text is now the third sub-bullet of the fourth bullet of
8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A> paragraph 14:</P>

<BLOCKQUOTE>

Otherwise (i.e., for the remaining copy-initialization cases),
user-defined conversion sequences that can convert from the source
type to the destination type or (when a conversion function is used)
to a derived class thereof are enumerated...
The function selected is called with the initializer expression as its
argument; if the function is a constructor, the call initializes a
temporary of the destination type.  The result of the call (which is
the temporary for the constructor case) is then used to
direct-initialize, according to the rules above, the object that is
the destination of the copy-initialization.

</BLOCKQUOTE>

<P>The issue still remains whether the wording should refer to "the
cv-unqualified version of the destination type."  I think it
should.
</P>

<P>
<B>Notes from 10/00 meeting:</B>
</P>

<P>The original example does not illustrate the remaining
problem.  The following example does:</P>

<PRE>
    struct C { };
    C c;
    struct A {
        A(const A&amp;);
        A(const C&amp;);
    };
    const volatile A a = c;    // Okay
</PRE>

<P>
<B>Proposed Resolution (04/01):</B>
</P>

<P>In 8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A>, paragraph 14, bullet 4,
sub-bullet 3, change</P>

<BLOCKQUOTE>

if the function is a constructor, the call initializes a temporary
of the destination type.

</BLOCKQUOTE>

<P>to</P>

<BLOCKQUOTE>

if the function is a constructor, the call initializes a temporary
of the cv-unqualified version of the destination type.

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="78"></A>
<H4>78.
  
Section 8.5 paragraph 9 should state it only applies to non-static objects
</H4>
<B>Section: </B>8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Judy Ward
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>15 Dec 1998<BR>



<P>Paragraph 9 of
8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A>

 says:</P>
<BLOCKQUOTE>If no initializer is specified for an object, and the object
is of (possibly cv-qualified) non-POD class type (or array thereof), the
object shall be default-initialized; if the object is of const-qualified
type, the underlying class type shall have a user-declared default constructor.
Otherwise, if no initializer is specified for an object, the object and
its subobjects, if any, have an indeterminate initial value; if the object
or any of its subobjects are of const-qualified type, the program is ill-formed.</BLOCKQUOTE>
It should be made clear that this paragraph does not apply to static objects.

<P>
<B>Proposed resolution (10/00):</B> In
8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A>
 paragraph 9, replace</P>
<BLOCKQUOTE>
Otherwise, if no initializer is specified for an object..."
</BLOCKQUOTE>
with
<BLOCKQUOTE>
Otherwise, if no initializer is specified for a <B>non-static</B>
object...
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="177"></A>
<H4>177.
  
Lvalues vs rvalues in copy-initialization
</H4>
<B>Section: </B>8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Adamczyk
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>25 October 1999<BR>



<P>[Moved to DR at 4/02 meeting.]</P>

<P>Is the temporary created during copy-initialization of a class object
treated as an lvalue or an rvalue?  That is, is the following example
well-formed or not?</P>

<PRE>
    struct B { };
    struct A {
        A(A&amp;);    // not const
        A(const B&amp;);
    };
    B b;
    A a = b;
</PRE>

<P>According to 8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A>
 paragraph
14, the initialization of <TT>a</TT> is performed in two steps.
First, a temporary of type <TT>A</TT> is created using <TT>A::A(const
B&amp;)</TT>.  Second, the resulting temporary is used to
direct-initialize <TT>a</TT> using <TT>A::A(A&amp;)</TT>.</P>

<P>The second step requires binding a reference to non-const to the
temporary resulting from the first step.  However,
8.5.3&nbsp;



 <A HREF="decl.html#dcl.init.ref">dcl.init.ref</A>
 paragraph 5 requires
that such a reference be bound only to lvalues.</P>

<P>It is not clear from 3.10&nbsp;



 <A HREF="basic.html#basic.lval">basic.lval</A>

whether the temporary created in the process of copy-initialization
should be treated as an lvalue or an rvalue.  If it is an lvalue, the
example is well-formed, otherwise it is ill-formed.</P>

<P>
<B>Proposed resolution (04/01):</B>
</P>

<OL>
<LI>
<P>In 8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A> paragraph 14, insert
the following after "the call initializes a temporary of
the destination type":</P>

<BLOCKQUOTE>

The temporary is an rvalue.

</BLOCKQUOTE>
</LI>

<LI>
<P>In 15.1&nbsp;



 <A HREF="except.html#except.throw">except.throw</A> paragraph 3, replace</P>

<BLOCKQUOTE>

The temporary is used to initialize the variable...

</BLOCKQUOTE>

<P>with</P>

<BLOCKQUOTE>

The temporary is an lvalue and is used to initialize
the variable...

</BLOCKQUOTE>

</LI>

</OL>

<P>(See also <A HREF="
     cwg_defects.html#84">issue 84</A>.)</P>
<BR>
<BR>
<HR>
<A NAME="277"></A>
<H4>277.
  
Zero-initialization of pointers
</H4>
<B>Section: </B>8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Andrew Sawyer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>5 Apr 2001<BR>


<P>[Moved to DR at 10/01 meeting.]</P>



<P>The intent of 8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A> paragraph 5 is that
pointers that are zero-initialized will contain a null pointer
value.  Unfortunately, the wording used,</P>

<BLOCKQUOTE>

...set to the value of 0 (zero) converted to <TT>T</TT>

</BLOCKQUOTE>

<P>does not match the requirements for creating a null pointer
value given in 4.10&nbsp;



 <A HREF="conv.html#conv.ptr">conv.ptr</A> paragraph 1:</P>

<BLOCKQUOTE>

A <I>null pointer constant</I> is an integral constant expression
(5.19&nbsp;



 <A HREF="expr.html#expr.const">expr.const</A>) rvalue of integer type that evaluates to
zero. A null pointer constant can be converted to a pointer type; the
result is the <I>null pointer value</I> of that type...

</BLOCKQUOTE>

<P>The problem is that the "value of 0" in the description of
zero-initialization is not specified to be an integral constant
expression.  Nonconstant expressions can also have the value 0,
and converting a nonconst 0 to pointer type need not result in
a null pointer value.</P>

<P>
<B>Proposed resolution (04/01):</B>
</P>

<P>In 8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A> paragraph 5, change</P>

<BLOCKQUOTE>

...set to the value 0 (zero) converted to <TT>T</TT>;

</BLOCKQUOTE>

<P>to</P>

<BLOCKQUOTE>

...set to the value 0 (zero), taken as an integral constant
expression, converted to <TT>T</TT>; [<I>footnote:</I> as
specified in 4.10&nbsp;



 <A HREF="conv.html#conv.ptr">conv.ptr</A>, converting an integral
constant expression whose value is 0 to a pointer type results
in a null pointer value.]

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="302"></A>
<H4>302.
  
Value-initialization and generation of default constructor
</H4>
<B>Section: </B>8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Adamczyk
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>23 Jul 2001<BR>


<P>[Moved to DR at October 2002 meeting.]</P>



<P>We've been looking at implementing value-initialization.  At one point,
some years back, I remember Bjarne saying that something like X() in
an expression should produce an X object with the same value one would
get if one created a static X object, i.e., the uninitialized members
would be zero-initialized because the whole object is initialized
at program startup, before the constructor is called.</P>

<P>The formulation for default-initialization that made it into TC1 (in
8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A>)
is written a little differently (see <A HREF="
     cwg_defects.html#178">issue 178</A>),
but I had always 
assumed that it would still be a valid implementation to zero the whole 
object and then call the default constructor for the troublesome
"non-POD but no user-written constructor" cases.</P>

<P>That almost works correctly, but I found a problem case:</P>
<PRE>
    struct A {
      A();
      ~A();
    };
    struct B {
      // B is a non-POD with no user-written constructor.
      // It has a nontrivial generated constructor.
      const int i;
      A a;
    };
    int main () {
      // Value-initializing a "B" doesn't call the default constructor for
      // "B"; it value-initializes the members of B.  Therefore it shouldn't
      // cause an error on generation of the default constructor for the
      // following:
      new B();
    }
</PRE>

<P>If the definition of the <TT>B::B()</TT> constructor is generated, an error
is issued because the const member "<TT>i</TT>" is not initialized.  But the
definition of value-initialization doesn't require calling the
constructor, and therefore it doesn't require generating it, and
therefore the error shouldn't be detected.</P>

<P>So this is a case where zero-initializing and then calling the constructor
is not equivalent to value-initializing, because one case generates
an error and the other doesn't.</P>

<P>This is sort of unfortunate, because one doesn't want to generate all
the required initializations at the point where the "<TT>()</TT>"
initialization
occurs.  One would like those initializations to be packaged in a
function, and the default constructor is pretty much the function
one wants.</P>

<P>I see several implementation choices:</P>
<OL>
<LI>
Zero the object, then call the default generated constructor.  This
is not valid unless the standard is changed to say that the default 
constructor might be generated for value-initialization cases like the
above (that is, it's implementation-dependent whether the constructor
definition is generated).  The zeroing operation can of course be
optimized, if necessary, to hit only the pieces of the object that
would otherwise be left uninitialized.  An alternative would be
to <I>require</I> generation of the constructor for value-initialization
cases, even if the implementation technique doesn't call the
constructor at that point.  It's pretty likely that the constructor
is going to have to be generated at some point in the program anyway.
</LI>
<LI>
Make a new value-initialization "constructor," whose body looks a
lot like the usual generated constructor, but which also zeroes other members.
No errors would be generated while generating this modified constructor,
because it generates code that does full initialization.  (Actually,
it wouldn't guarantee initialization of reference members, and that
might be an argument for generating the constructor, in order to get that
error.)  This is standard-conforming, but it destroys object-code 
compatibility.
</LI>
<LI>
Variation on (1):  Zero first, and generate the object code for the 
default constructor when it's needed for value-initialization cases, but 
don't issue any errors at that time.  Issue the errors only if it turns 
out the constructor is "really" referenced.  Aside from the essential
shadiness of this approach, I fear that something in the generation
of the constructor will cause a template instantiation which will be
an abservable side effect.
</LI>
</OL>

<P>Personally, I find option 1 the least objectionable.</P>

<P>
<B>Proposed resolution (10/01):</B>
</P>

<P>Add the indicated wording to the third-to-last sentence of
3.2&nbsp;



 <A HREF="basic.html#basic.def.odr">basic.def.odr</A> pararaph 2:</P>
<BLOCKQUOTE>
A default constructor for a class is used by default initialization
<B>or value initialization</B> as specified in 8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A>.
</BLOCKQUOTE>
<P>Add a footnote to the indicated bullet in 8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A>
paragraph 5:</P>
<UL>
<LI>
if <TT>T</TT> is a non-union class type without a user-declared constructor,
then every non-static data member and base-class component of <TT>T</TT> is
value-initialized.
<B>[Footnote: Value-initialization for such a class object may be
implemented by zero-initializing the object and then calling the default
constructor.]</B>
</LI>
</UL>
<P>Add the indicated wording to the first sentence of
12.1&nbsp;



 <A HREF="special.html#class.ctor">class.ctor</A> paragraph 7:</P>
<BLOCKQUOTE>
An implicitly-declared default constructor for a class is <I>implicitly
defined</I> when it is used <B>(3.2&nbsp;



 <A HREF="basic.html#basic.def.odr">basic.def.odr</A>)</B> to
create an object of its class type
(1.8&nbsp;



 <A HREF="intro.html#intro.object">intro.object</A>).
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="291"></A>
<H4>291.
  
Overload resolution needed when binding reference to class rvalue
</H4>
<B>Section: </B>8.5.3&nbsp;



 <A HREF="decl.html#dcl.init.ref">dcl.init.ref</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Andrei Iltchenko
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>15 Jun 2001<BR>


<P>[Voted into WP at October 2005 meeting.]</P>

<P>There is a place in the Standard where overload resolution is implied
but the way that a set of candidate functions is to be formed is
omitted. See below.</P>

<P>According to the Standard, when initializing a reference to a
non-volatile const class type (<I>cv1</I> <TT>T1</TT>) with an rvalue
expression (<I>cv2</I> <TT>T2</TT>) where <I>cv1</I> <TT>T1</TT> is
reference compatible with <I>cv2</I> <TT>T2</TT>, the implementation
shall proceed in one of the following
ways (except when initializing the implicit object parameter of a
copy constructor) 8.5.3&nbsp;



 <A HREF="decl.html#dcl.init.ref">dcl.init.ref</A> paragraph 5 bullet 2
sub-bullet 1:</P>

<UL>
<LI>
The reference is bound to the object represented by the rvalue (see
3.10&nbsp;



 <A HREF="basic.html#basic.lval">basic.lval</A>) or to a sub-object within that object.
</LI>
<LI>
A temporary of type "<I>cv1</I> <TT>T2</TT>" [sic] is created, and a
constructor is called to copy the entire rvalue object into the temporary...
</LI>
</UL>

<P>While the first case is quite obvious, the second one is a bit unclear
as it says "a constructor is called to copy the entire rvalue object
into the temporary" without specifying how the temporary is created --
by direct-initialization or by copy-initialization? As stated in DR
152, this can make a difference when the copy constructor is declared
as explicit. How should the set of candidate functions be formed? The
most appropriate guess is that it shall proceed as per
13.3.1.3&nbsp;



 <A HREF="over.html#over.match.ctor">over.match.ctor</A>.</P>

<P>Another detail worth of note is that in the draft version of the
Standard as of 2 December 1996 the second bullet read:</P>

<UL>
<LI>
A temporary of type "<I>cv1</I> <TT>T2</TT>" [sic] is created, and a copy
constructor is called to copy the entire rvalue object into the
temporary...
</LI>
</UL>

<P>J. Stephen Adamczyk replied that the reason for changing "a copy
constructor" to "a constructor" was to allow for member template
converting constructors.</P>

<P>However, the new wording is somewhat in conflict with the footnote #93
that says that when initializing the implicit object parameter of a
copy constructor an implementation must eventually choose the first
alternative (binding without copying) to avoid infinite recursion.
This seems to suggest that a copy constructor is always used for
initializing the temporary of type "<I>cv1</I> <TT>T2</TT>".</P>

<P>Furthermore, now that the set of candidate functions is not limited to
only the copy constructors of <TT>T2</TT>, there might be some unpleasant
consequences.
Consider a rather contrived sample below:</P>

<PRE>
    int   * pi = ::new(std::nothrow) int;
    const std::auto_ptr&lt;int&gt;   &amp; ri = std::auto_ptr&lt;int&gt;(pi);
</PRE>

<P>In this example the initialization of the temporary of type
'<TT>&lt;TT&gt;const std::auto_ptr&lt;int&gt;</TT>'
(to which '<TT>ri</TT>' is meant to be subsequently bound)
doesn't fail, as it would had the approach with copy constructors been
retained, instead, a yet another temporary gets created as the
well-known sequence:</P>
<PRE>
    std::auto_ptr&lt;int&gt;::operator std::auto_ptr_ref&lt;int&gt;()
    std::auto_ptr&lt;int&gt;(std::auto_ptr_ref&lt;int&gt;)
</PRE>
<P>is called (assuming, of course, that the set of candidate functions is
formed as per 13.3.1.3&nbsp;



 <A HREF="over.html#over.match.ctor">over.match.ctor</A>). The second temporary
is transient and gets
destroyed at the end of the initialization. I doubt that this is the
way that the committee wanted this kind of reference binding to go.</P>

<P>Besides, even if the approach restricting the set of candidates to copy
constructors is restored, it is still not clear how the initialization
of the temporary (to which the reference is intended to be bound) is
to be performed -- using direct-initialization or copy-initialization.</P>

<P>Another place in the Standard that would benefit from a similar
clarification is the creation of an exception object, which is
delineated in 15.1&nbsp;



 <A HREF="except.html#except.throw">except.throw</A>.</P>

<P>
<U>David Abrahams (February 2004):</U>
It appears, looking at core 291, that there may be a need to tighten
up 8.5.3&nbsp;



 <A HREF="decl.html#dcl.init.ref">dcl.init.ref</A>/5.  </P>

<P>Please see the attached example file, which demonstrates "move
semantics" in C++98.  Many compilers fail to compile test 10 because
of the way 8.5.3/5 is interpreted.  My problem with that
interpretation is that test 20:
<PRE>
    typedef X const XC;
    sink2(XC(X()));
</PRE>
does compile.  In other words, it *is* possible to construct the const
temporary from the rvalue.  IMO, that is the proper test.</P>

<P>8.5.3/5 doesn't demand that a "copy constructor" is used to copy the
temporary, only that a constructor is used "to copy the temporary".
I hope that when the language is tightened up to specify direct (or
copy initialization), that it also unambiguously allows the enclosed
test to compile.  Not only is it, I believe, within the scope of
reasonable interpretation of the current standard, but it's an
incredibly important piece of functionality for library writers and
users alike.</P>

<PRE>
#include &lt;iostream&gt;
#include &lt;cassert&gt;

template &lt;class T, class X&gt;
struct enable_if_same
{
};

template &lt;class X&gt;
struct enable_if_same&lt;X, X&gt;
{
    typedef char type;
};

struct X
{
    static int cnt;  // count the number of Xs
    
    X()
      : id(++cnt)
      , owner(true)
    {
        std::cout &lt;&lt; "X() #" &lt;&lt; id &lt;&lt; std::endl;
    }
    
    // non-const lvalue - copy ctor
    X(X&amp; rhs)
      : id(++cnt)
      , owner(true)
    {
        std::cout &lt;&lt; "copy #" &lt;&lt; id &lt;&lt; " &lt;- #" &lt;&lt; rhs.id &lt;&lt; std::endl;
    }

    // const lvalue - T will be deduced as X const
    template &lt;class T&gt;
    X(T&amp; rhs, typename enable_if_same&lt;X const,T&gt;::type = 0)
      : id(++cnt)
      , owner(true)
    {
        std::cout &lt;&lt; "copy #" &lt;&lt; id &lt;&lt; " &lt;- #" &lt;&lt; rhs.id &lt;&lt; " (const)" &lt;&lt; std::endl;
    }

    ~X()
    {
        std::cout &lt;&lt; "destroy #" &lt;&lt; id &lt;&lt; (owner?"":" (EMPTY)") &lt;&lt; std::endl;
    }
    
 private:    // Move stuff
    struct ref { ref(X*p) : p(p) {} X* p; };

 public:    // Move stuff
    operator ref() {
        return ref(this);
    }

    // non-const rvalue
    X(ref rhs)
      : id(++cnt)
      , owner(rhs.p-&gt;owner)
    {
        std::cout &lt;&lt; "MOVE #" &lt;&lt; id &lt;&lt; " &lt;== #" &lt;&lt; rhs.p-&gt;id &lt;&lt; std::endl;
        rhs.p-&gt;owner = false;
        assert(owner);
    }
    
 private:   // Data members
    int id;
    bool owner;
};

int X::cnt;


X source()
{
    return X();
}

X const csource()
{
    return X();
}

void sink(X)
{
    std::cout &lt;&lt; "in rvalue sink" &lt;&lt; std::endl;
}

void sink2(X&amp;)
{
    std::cout &lt;&lt; "in non-const lvalue sink2" &lt;&lt; std::endl;
}

void sink2(X const&amp;)
{
    std::cout &lt;&lt; "in const lvalue sink2" &lt;&lt; std::endl;
}

void sink3(X&amp;)
{
    std::cout &lt;&lt; "in non-const lvalue sink3" &lt;&lt; std::endl;
}

template &lt;class T&gt;
void tsink(T)
{
    std::cout &lt;&lt; "in templated rvalue sink" &lt;&lt; std::endl;
}

int main()
{
    std::cout &lt;&lt; " ------ test 1, direct init from rvalue ------- " &lt;&lt; std::endl;
#ifdef __GNUC__ // GCC having trouble parsing the extra parens
    X z2((0, X() ));
#else
    X z2((X()));
#endif 

    std::cout &lt;&lt; " ------ test 2, copy init from rvalue ------- " &lt;&lt; std::endl;
    X z4 = X();

    std::cout &lt;&lt; " ------ test 3, copy init from lvalue ------- " &lt;&lt; std::endl;
    X z5 = z4;

    std::cout &lt;&lt; " ------ test 4, direct init from lvalue ------- " &lt;&lt; std::endl;
    X z6(z4);
    
    std::cout &lt;&lt; " ------ test 5, construct const ------- " &lt;&lt; std::endl;
    X const z7;
    
    std::cout &lt;&lt; " ------ test 6, copy init from lvalue ------- " &lt;&lt; std::endl;
    X z8 = z7;

    std::cout &lt;&lt; " ------ test 7, direct init from lvalue ------- " &lt;&lt; std::endl;
    X z9(z7);
    
    std::cout &lt;&lt; " ------ test 8, pass rvalue by-value ------- " &lt;&lt; std::endl;
    sink(source());
    
    std::cout &lt;&lt; " ------ test 9, pass const rvalue by-value ------- " &lt;&lt; std::endl;
    sink(csource());

    std::cout &lt;&lt; " ------ test 10, pass rvalue by overloaded reference ------- " &lt;&lt; std::endl;
    // This one fails in Comeau's strict mode due to 8.5.3/5.  GCC 3.3.1 passes it.
    sink2(source());

    std::cout &lt;&lt; " ------ test 11, pass const rvalue by overloaded reference ------- " &lt;&lt; std::endl;
    sink2(csource());

#if 0    // These two correctly fail to compile, just as desired
    std::cout &lt;&lt; " ------ test 12, pass rvalue by non-const reference ------- " &lt;&lt; std::endl;
    sink3(source());

    std::cout &lt;&lt; " ------ test 13, pass const rvalue by non-const reference ------- " &lt;&lt; std::endl;
    sink3(csource());
#endif 

    std::cout &lt;&lt; " ------ test 14, pass lvalue by-value ------- " &lt;&lt; std::endl;
    sink(z5);
    
    std::cout &lt;&lt; " ------ test 15, pass const lvalue by-value ------- " &lt;&lt; std::endl;
    sink(z7);

    std::cout &lt;&lt; " ------ test 16, pass lvalue by-reference ------- " &lt;&lt; std::endl;
    sink2(z4);

    std::cout &lt;&lt; " ------ test 17, pass const lvalue by const reference ------- " &lt;&lt; std::endl;
    sink2(z7);

    std::cout &lt;&lt; " ------ test 18, pass const lvalue by-reference ------- " &lt;&lt; std::endl;
#if 0   // correctly fails to compile, just as desired
    sink3(z7);
#endif 

    std::cout &lt;&lt; " ------ test 19, pass rvalue by value to template param ------- " &lt;&lt; std::endl;
    tsink(source());

    std::cout &lt;&lt; " ------ test 20, direct initialize a const A with an A ------- " &lt;&lt; std::endl;
    typedef X const XC;
    sink2(XC(X()));
}
</PRE>

<P>
<B>Proposed Resolution:</B>
</P>

<P>(As proposed by N1610 section 5, with editing.)</P>

<P>Change  paragraph 5, second bullet,
first sub-bullet, second sub-sub-bullet as follows:</P>
<BLOCKQUOTE>
A temporary of type "<I>cv1</I> <TT>T2</TT>" [sic] is created<S>, and a
constructor is called to copy the entire rvalue object into the temporary</S>
<B>via copy-initialization from the entire rvalue object</B>.
The  reference  is  bound  to  the  temporary or to a sub-object
within the temporary.
</BLOCKQUOTE>

<P>The text immediately following that is changed as follows:</P>
<BLOCKQUOTE>
<S>The  constructor  that  would  be  used  to make the copy shall be
callable whether or not the copy is actually done.</S>
<B>The constructor and any conversion function that would be used in the
initialization shall be callable whether or not the temporary is
actually created. </B>
</BLOCKQUOTE>

<P>Note, however, that the way the core working group is leaning
on <A HREF="
     cwg_defects.html#391">issue 391</A> (i.e., requiring direct
binding) would make this change unnecessary.</P>

<P>
<B>Proposed resolution (April, 2005):</B>
</P>

<P>This issue is resolved by the resolution of <A HREF="
     cwg_defects.html#391">issue 391</A>.</P>

<BR>
<BR>
<HR>
<A NAME="391"></A>
<H4>391.
  
Require direct binding of short-lived references to rvalues
</H4>
<B>Section: </B>8.5.3&nbsp;



 <A HREF="decl.html#dcl.init.ref">dcl.init.ref</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Raoul Gough
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>14 Nov 2002<BR>


<P>[Voted into WP at October 2005 meeting.]</P>

<P>After some email exchanges with Rani Sharoni, I've come up
with the following proposal to allow reference binding to
non-copyable rvalues in some cases. Rationale and some
background appear afterwards.</P>

<P>
<B>---- proposal ----</B>
</P>

<P>Replace the section of 8.5.3&nbsp;



 <A HREF="decl.html#dcl.init.ref">dcl.init.ref</A> paragraph 5
that begins "If the initializer expression is an rvalue" with the
following:</P>
<UL>
<LI>
If the initializer expression is an rvalue, with T2 a
class type, and ``cv1 T1'' is reference-compatible with
``cv2 T2,'' the reference is bound as follows:
<UL>
<LI>
If the lifetime of the reference does not extend
beyond the end of the full expression containing the
initializer expression, the reference is bound to
the object represented by the rvalue (see 3.10&nbsp;



 <A HREF="basic.html#basic.lval">basic.lval</A>) or
to a sub-object within that object.
</LI>
<LI>
otherwise, the reference is bound in one of the
following ways (the choice is implementation-defined):
<UL>
<LI>
[... continues as before - the original wording applies
unchanged to longer-lived references]
</LI>
</UL>
</LI>
</UL>
</LI>
</UL>

<P>
<B>---- rationale ----</B>
</P>

<OL>
<LI>
The intention of the current wording is to provide the
   implementation freedom to construct an rvalue of class
   type at an arbitrary location and copy it zero <U>or more</U>
   times before binding any reference to it.
</LI>
<LI>
The standard allows code to call a member function on an
   rvalue of class type (in 5.2.5&nbsp;



 <A HREF="expr.html#expr.ref">expr.ref</A>, I guess).
This means that
   the implementation can be forced to bind the reference
   directly, with no freedom to create any temporary
   copies. e.g.
<PRE>
   class nc {
     nc (nc const &amp;);  // private, nowhere defined
   public:
     nc ();
     nc const &amp;by_ref () const { return *this; }
   };

   void f () {
     void g (nc const &amp;);

     g (nc());          // Ill-formed
     g (nc().by_ref()); // Ok - binds directly to rvalue
   }
</PRE>

   Forcing a direct binding in this way is possible wherever
   the lifetime of the reference does not extend beyond the
   containing full expression, since the reference returned
   by the member function remains valid for this long.
</LI>
<LI>
As demonstrated above, existing implementations must
   already be capable of constructing an rvalue of class
   type in the "right" place the first time. Some compilers
   already silently allow the direct binding of references
   to non-copyable rvalues.
</LI>
<LI>
The change will not break any portable user code. It
   would break any platform-specific user code that relies
   on copies being performed by the particular
   implementation.
</LI>
</OL>

<P>
<B>---- background ----</B>
</P>

<P>The proposal is based on a recent discussion in this
group. I originally wanted to leave the implementation free
to copy the rvalue if there was a callable copy constructor,
and only <B>have</B> to bind directly if none was callable.
Unfortunately, a traditional compiler can't always tell
whether a function is callable or not, e.g. if the copy
constructor is declared but not defined. Rani pointed this
out in an example, and suggested that maybe trivial copy
constructors should still be allowed (by extension, maybe
wherever the compiler can determine callability). I've gone
with this version because it's simpler, and I also figure
the "as if" rule gives the compiler some freedom with POD
types anyway.</P>

<P>
<B>Notes from April 2003 meeting:</B>
</P>

<P>We agreed generally with the proposal.  We were unsure about the
need for the restriction regarding long-lived references.
We will check with the proposer about that.</P>

<P>Jason Merrill points out that the test case in
<A HREF="
     cwg_defects.html#86">issue 86</A> may be a case where we
do not want to require direct binding.</P>

<P>
<B>Further information from Rani Sharoni (April 2003):</B>
</P>

<P>I wasn't aware about the latest suggestion of Raoul as it appears in
core issue 391. In our discussions we tried to formulate a different
proposal.</P>
<P>The rational, as we understood, behind the implementation freedom to
make an extra copying (8.5.3/5/2/12) of the rvalue is to allow return
values in registers which on some architectures are not addressable.
The example that Raoul and I presented shows that this implementation
freedom is not always possible since we can "force" the rvalue to be
addressable using additional member function (by_ref). The example
only works for short lived rvalues and this is probably why Raoul
narrow the suggestion.</P>
<P>I had different rational which was related to the implementation of
conditional operator in VC. It seems that when conditional operator is
involved VC does use an extra copying when the lifetime of the
temporary is extended:</P>
<PRE>
  struct A { /* ctor with side effect */};

  void f(A&amp; x) {
    A const&amp; r = cond ? A(1) : x; // VC actually make an extra copy of
                                  // the rvalue A(1)
  }
</PRE>
<P>I don't know what the consideration behind the VC implementation was
(I saw open bug on this issue) but it convinced me to narrow the
suggestion.</P>

<P>IMHO such limitation seems to be too strict because it might limit the
optimizer since returning class rvalues in registers might be useful
(although I'm not aware about any implementation that actually does
it). My suggestion was to forbid the extra copying if the ctor is not
viable (e.g. A::A(A&amp;) ). In this case the implementation "freedom"
doesn't exist (since the code might not compile) and only limits the
programmer freedom (e.g. Move Constructors -
<A HREF="http://www.cuj.com/experts/2102/alexandr.htm">
http://www.cuj.com/experts/2102/alexandr.htm</A>).</P>

<P>
<A HREF="
     cwg_defects.html#291">Core issue 291</A> is strongly related to
the above issue and I personally
prefer to see it resolved first. It seems that VC already supports the
resolution I prefer.</P>

<P>
<B>Notes from October 2003 meeting:</B>
</P>

<P>We ended up feeling that this is just one of a number of cases
of optimizations that are widely done by compilers
and allowed but not required by the standard.  We don't see any
strong reason to require compilers to do this particular
optimization.</P>

<P>
<B>Notes from the March 2004 meeting:</B>
</P>

<P>After discussing <A HREF="
     cwg_defects.html#450">issue 450</A>, we
found ourselves reconsidering this, and we are now inclined to
make a change to require the direct binding in all cases,
with no restriction on long-lived references.  Note that such
a change would eliminate the need for a change for
<A HREF="
     cwg_defects.html#291">issue 291</A>.</P>

<P>
<B>Proposed resolution (October, 2004):</B>
</P>

<P>Change 8.5.3&nbsp;



 <A HREF="decl.html#dcl.init.ref">dcl.init.ref</A> paragraph 5 bullet 2
sub-bullet 1 as follows:</P>

<BLOCKQUOTE>
If the initializer expression is an rvalue, with <TT>T2</TT> a class type,
and "<I>cv1</I> <TT>T1</TT>" is reference-compatible with
"<I>cv2</I> <TT>T2</TT>", the reference is bound <B>to the
object represented by the rvalue (see 3.10&nbsp;



 <A HREF="basic.html#basic.lval">basic.lval</A>) or to a sub-object within that object.</B>
<S>in one of the following ways (the choice is
implementation-defined):
<UL>

<LI>
The reference is bound to the object represented by the
rvalue (see 3.10&nbsp;



 <A HREF="basic.html#basic.lval">basic.lval</A>) or to a sub-object
within that object.  </LI>

<LI>
A temporary of type "<I>cv1</I> <TT>T2</TT>" [sic] is created, and a
constructor is called to copy the entire rvalue object into the
temporary. The reference is bound to the temporary or to a
sub-object within the temporary.
</LI>

</UL>

The constructor that would be used to make the copy shall be
callable whether or not the copy is actually done.</S>
[<I>Example:</I>

<PRE>
  struct A { };
  struct B : public A { } b;
  extern B f();
  const A&amp; rca = f ();  // <B>Bound</B> <S>Either bound</S> to the A sub-object of the B rvalue<S>,
                        // or the entire B object is copied and the reference
                        // is bound to the A sub-object of the copy</S>
</PRE>
&mdash;<I>end example</I>]
</BLOCKQUOTE>

<P>
<I>[This resolution also resolves <A HREF="
     cwg_defects.html#291">issue 291</A>.]</I>
</P>

<BR>
<BR>
<HR>
<A NAME="450"></A>
<H4>450.
  
Binding a reference to const to a cv-qualified array rvalue
</H4>
<B>Section: </B>8.5.3&nbsp;



 <A HREF="decl.html#dcl.init.ref">dcl.init.ref</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Adamczyk
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>16 Jan 2004<BR>


<P>[Voted into WP at October 2005 meeting.]</P>

<P>It's unclear whether the following is valid:</P>
<PRE>
const int N = 10;
const int M = 20;
typedef int T;
void f(T const (&amp;x)[N][M]){}

struct X {
	int i[10][20];
};

X g();

int main()
{
	f(g().i);
}
</PRE>
<P>When you run this through 8.5.3&nbsp;



 <A HREF="decl.html#dcl.init.ref">dcl.init.ref</A>, you sort of end up
falling off the end of the standard's description of reference
binding.  The standard says in the final bullet of paragraph 5
that an array temporary should be created and copy-initialized
from the rvalue array, which seems implausible.</P>

<P> I'm not sure what the right answer is.  I think I'd be happy with
allowing the binding in this case.  We would have to introduce
a special case like the one for class rvalues.</P>

<P>
<B>Notes from the March 2004 meeting:</B>
</P>

<P>g++ and EDG give an error.  Microsoft (8.0 beta) and Sun accept
the example.  Our preference is to allow the direct binding (no copy).
See the similar issue with class rvalues in
<A HREF="
     cwg_defects.html#391">issue 391</A>.</P>

<P>
<B>Proposed resolution (October, 2004):</B>
</P>

<OL>

<LI>
<P>Insert a new bullet in 8.5.3&nbsp;



 <A HREF="decl.html#dcl.init.ref">dcl.init.ref</A>
paragraph 5 bullet 2 before sub-bullet 2 (which begins,
&ldquo;Otherwise, a temporary of type &lsquo;<I>cv1</I>
<TT>T1</TT>&rsquo; is created...&rdquo;):</P>

<BLOCKQUOTE>

If the initializer expression is an rvalue, with <TT>T2</TT> an
array type, and &ldquo;<I>cv1</I> <TT>T1</TT>&rdquo; is
reference-compatible with &ldquo;<I>cv2</I> <TT>T2</TT>&rdquo;,
the reference is bound to the object represented by the rvalue
(see 3.10&nbsp;



 <A HREF="basic.html#basic.lval">basic.lval</A>).

</BLOCKQUOTE>

</LI>

<LI>
<P>Change 3.10&nbsp;



 <A HREF="basic.html#basic.lval">basic.lval</A> paragraph 2 as
follows:</P>

<BLOCKQUOTE>

An lvalue refers to an object or function. Some rvalue
expressions &mdash; those of <B>(possibly cv-qualified)</B> class
<B>or array type</B> <S>or cv-qualified class type</S> &mdash;
also refer to objects.

</BLOCKQUOTE>

</LI>

</OL>

<BR>
<BR>
<HR>
<A NAME="175"></A>
<H4>175.
  
Class name injection and base name access
</H4>
<B>Section: </B>9&nbsp;



 <A HREF="class.html#class">class</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>John Spicer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>21 February 1999<BR>



<P>[Moved to DR at 10/01 meeting.]</P>

<P>With class name injection, when a base class name is used in a derived
class, the name found is the injected name in the base class, not the
name of the class in the scope containing the base class.
Consequently, if the base class name is not accessible (e.g., because
is is in a private base class), the base class name cannot be used
unless a qualified name is used to name the class in the class or
namespace of which it is a member.</P>

<P>Without class name injection the following example is valid.  With
class name injection, <TT>A</TT> is inaccessible in class <TT>C</TT>.</P>

<PRE>
    class A { };
    class B: private A { };
    class C: public B {
        A* p;    // error: A inaccessible
    };
</PRE>

<P>At the least, the standard should be more explicit that this is, in
fact, ill-formed.</P>

<P>(See paper J16/99-0010 = WG21 N1187.)</P>

<P>
<B>Proposed resolution (04/01):</B>
</P>

<P>Add to the end of 11.1&nbsp;



 <A HREF="access.html#class.access.spec">class.access.spec</A> paragraph 3:</P>

<BLOCKQUOTE>

<P>[<I>Note:</I> In a derived class, the lookup of a base class name
will find the injected-class-name instead of the name of the base
class in the scope in which it was declared.  The
injected-class-name might be less accessible than the name of the
base class in the scope in which it was declared.] [<I>Example:</I>
</P>

<PRE>
    class A { };
    class B : private A { };
    class C : public B {
        A* p;    // error: injected-class-name A is inaccessible
        ::A* q;  // OK
    };
</PRE>

<P>&mdash;<I>end example</I>]</P>

</BLOCKQUOTE>
<BR>
<BR>
<HR>
<A NAME="273"></A>
<H4>273.
  
POD classes and <TT>operator&amp;()</TT>
</H4>
<B>Section: </B>9&nbsp;



 <A HREF="class.html#class">class</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Andrei Iltchenko
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>10 Mar 2001<BR>


<P>[Moved to DR at October 2002 meeting.]</P>

<P>I think that the definition of a POD class in the current version
of the Standard is overly permissive in that it allows for POD classes
for which a user-defined operator function <TT>operator&amp;</TT> may
be defined. Given that the idea behind POD classes was to achieve
compatibility with C structs and unions, this makes 'Plain old'
structs and unions behave not quite as one would expect them to.</P>

<P>In the C language, if <TT>x</TT> and <TT>y</TT> are variables of
struct or union type <TT>S</TT> that has a member <TT>m</TT>, the
following expression are allowed: <TT>&amp;x</TT>, <TT>x.m</TT>, <TT>x
= y</TT>.  While the C++ standard guarantees that if <TT>x</TT> and
<TT>y</TT> are objects of a POD class type <TT>S</TT>, the expressions
<TT>x.m</TT>, <TT>x = y</TT> will have the same effect as they would
in C, it is still possible for the expression <TT>&amp;x</TT> to be
interpreted differently, subject to the programmer supplying an
appropriate version of a user-defined operator function
<TT>operator&amp;</TT> either as a member function or as a non-member
function.</P>

<P>This may result in surprising effects. Consider:</P>

<PRE>
    // POD_bomb is a POD-struct. It has no non-static non-public data members,
    // no virtual functions, no base classes, no constructors, no user-defined
    // destructor, no user-defined copy assignment operator, no non-static data
    // members of type pointer to member, reference, non-POD-struct, or
    // non-POD-union.
    struct  POD_bomb  {
       int   m_value1;
       int   m_value2;
       int  operator&amp;()
       {   return  m_value1++;   }
       int  operator&amp;() const
       {   return  m_value1 + m_value2;   }
    };
</PRE>

<P>3.9&nbsp;



 <A HREF="basic.html#basic.types">basic.types</A> paragraph 2 states:</P>

<BLOCKQUOTE>

For any complete POD object type <TT>T</TT>, whether or not the object
holds a valid value of type <TT>T</TT>, the underlying bytes
(1.7&nbsp;



 <A HREF="intro.html#intro.memory">intro.memory</A>) making up the object can be copied into
an array of <TT>char</TT> or <TT>unsigned char</TT> [<I>footnote</I>:
By using, for example, the library functions (17.4.1.2&nbsp;



 <A HREF="lib-intro.html#lib.headers">lib.headers</A>) <TT>memcpy</TT> or <TT>memmove</TT>]. If the
content of the array of <TT>char</TT> or <TT>unsigned char</TT> is
copied back into the object, the object shall subsequently hold its
original value. [<I>Example</I>:

<PRE>
    #define N sizeof(T)
    char buf[N];
    T obj;   // obj initialized to its original value
    memcpy(buf, &amp;obj, N);
		// between these two calls to memcpy,
		// obj might be modified
    memcpy(&amp;obj, buf, N);
		// at this point, each subobject of obj of scalar type
		// holds its original value
</PRE>
&mdash;<I>end example</I>]
</BLOCKQUOTE>

<P>Now, supposing that the complete POD object type <TT>T</TT> in the
example above is <TT>POD_bomb</TT>, and we cannot any more count on
the assertions made in the comments to the example. Given a standard
conforming implementation, the code will not even compile. And I see
no legal way of copying the contents of an object of a complete object
type <TT>POD_bomb</TT> into an array of <TT>char</TT> or <TT>unsigned
char</TT> with <TT>memcpy</TT> or <TT>memmove</TT> without making use
of the unary <TT>&amp;</TT> operator. Except, of course, by means of
an ugly construct like:</P>

<PRE>
    struct  POD_without_ampersand  {
       POD_bomb   a_bomb;
    }  obj;
    #define N sizeof(POD_bomb)
    char buf[N];
    memcpy(buf, &amp;obj, N);
    memcpy(&amp;obj, buf, N);
</PRE>

<P>The fact that the definition of a POD class allows for POD classes
for which a user-defined <TT>operator&amp;</TT> is defined, may also
present major obstacles to implementers of the offsetof macro from
&lt;cstddef&gt;</P>

<P>18.1&nbsp;



 <A HREF="lib-support.html#lib.support.types">lib.support.types</A> paragraph 5 says:</P>

<BLOCKQUOTE>

The macro <TT>offsetof</TT> accepts a restricted set of type arguments
in this International Standard. <TT>type</TT> shall be a POD structure
or a POD union (clause 9&nbsp;



 <A HREF="class.html#class">class</A>). The result of
applying the <TT>offsetof</TT> macro to a field that is a static data
member or a function is undefined."

</BLOCKQUOTE>

<P>Consider a well-formed C++ program below:</P>

<PRE>
    #include &lt;cstddef&gt;
    #include &lt;iostream&gt;


    struct  POD_bomb  {
       int   m_value1;
       int   m_value2;
       int  operator&amp;()
       {   return  m_value1++;   }
       int  operator&amp;() const
       {   return  m_value1 + m_value2;   }
    };


    // POD_struct is a yet another example of a POD-struct.
    struct  POD_struct  {
       POD_bomb   m_nonstatic_bomb1;
       POD_bomb   m_nonstatic_bomb2;
    };


    int  main()
    {

       std::cout &lt;&lt; "offset of m_nonstatic_bomb2: " &lt;&lt; offsetof(POD_struct,
           m_nonstatic_bomb2) &lt;&lt; '\n';
       return  0;

    }
</PRE>

<P>See Jens Maurer's paper 01-0038=N1324 for an analysis of this issue.</P>

<P>
<B>Notes from 10/01 meeting:</B>
</P>

<P>A consensus was forming around the idea of disallowing
<TT>operator&amp;</TT> in POD classes when it was noticed that it is
permitted to declare global-scope <TT>operator&amp;</TT> functions,
which cause the same problems.  After more discussion, it was
decided that such functions should not be prohibited in POD classes,
and implementors should simply be required to "get the right answer"
in constructs such as <TT>offsetof</TT> and <TT>va_start</TT> that
are conventionally implemented using macros that use the "<TT>&amp;</TT>"
operator.  It was noted that one can cast the original operand to
<TT>char &amp;</TT> to de-type it, after which one can use the
built-in "<TT>&amp;</TT>" safely.</P>

<P>
<B>Proposed resolution:</B>
</P>

<UL>
<LI>Add a footnote in 18.1&nbsp;



 <A HREF="lib-support.html#lib.support.types">lib.support.types</A> paragraph 5:
<BLOCKQUOTE>
[<EM>Footnote:</EM> Note that <TT>offsetof</TT> is required to
work as specified even if unary <TT>operator&amp;</TT> is
overloaded for any of the types involved.]
</BLOCKQUOTE>
</LI>
<LI>Add a footnote in 18.7&nbsp;



 <A HREF="lib-support.html#lib.support.runtime">lib.support.runtime</A> paragraph 3:
<BLOCKQUOTE>
[<EM>Footnote:</EM> Note that <TT>va_start</TT> is required to
work as specified even if unary <TT>operator&amp;</TT> is
overloaded for the type of <TT>parmN</TT>.]
</BLOCKQUOTE>
</LI>
</UL>

<BR>
<BR>
<HR>
<A NAME="284"></A>
<H4>284.
  
<I>qualified-id</I>s in class declarations
</H4>
<B>Section: </B>9&nbsp;



 <A HREF="class.html#class">class</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>01 May 2001<BR>


<P>[Moved to DR at October 2002 meeting.]</P>

<P>Although 8.3&nbsp;



 <A HREF="decl.html#dcl.meaning">dcl.meaning</A> requires that a declaration of
a <I>qualified-id</I> refer to a member of the specified namespace or
class and that the member not have been introduced by a
<I>using-declaration</I>, it applies only to names declared in a
declarator.  It is not clear whether there is existing wording
enforcing the same restriction for <I>qualified-id</I>s in
<I>class-specifier</I>s and <I>elaborated-type-specifier</I>s or
whether additional wording is required.  Once such wording is
found/created, the proposed resolution of
<A HREF="
     cwg_defects.html#275">issue 275</A> must be modified accordingly.</P>

<P>
<B>Notes from 10/01 meeting:</B>
</P>

<P>The sentiment was that this should be required on class definitions, but
not on elaborated type specifiers in general (which are references, not
declarations).  We should also make sure we consider explicit instantiations,
explicit specializations, and friend declarations.</P>


<P>
<B>Proposed resolution (10/01):</B>
</P>

<P>Add after the end of 9.1&nbsp;



 <A HREF="class.html#class.name">class.name</A> paragraph 3:</P>
<BLOCKQUOTE>
When a <I>nested-name-specifier</I> is specified in a
<I>class-head</I> or in an
<I>elaborated-type-specifier</I>, the resulting qualified name
shall refer to a previously declared member of the class or namespace to
which the <I>nested-name-specifier</I> refers, and
the member shall not have been introduced by a
using-declaration in the scope of the class or namespace
nominated by the <I>nested-name-specifier</I>.
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="379"></A>
<H4>379.
  
Change "class declaration" to "class definition"
</H4>
<B>Section: </B>9&nbsp;



 <A HREF="class.html#class">class</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Jens Maurer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>21 Oct 2002<BR>


<P>[Voted into WP at March 2004 meeting.]</P>

<P>The ARM used the term "class declaration" to refer to what
would usually be termed the definition of the class.  The standard
now often uses "class definition", but there are some surviving uses
of "class declaration" with the old meaning.  They should be found
and changed.</P>

<P>
<B>Proposed resolution (April 2003):</B>
</P>

<P>
Replace in 3.1&nbsp;



 <A HREF="basic.html#basic.def">basic.def</A> paragraph 2</P>

<BLOCKQUOTE>
A declaration is a <I>definition</I> unless it declares a function
without specifying the function's body
(8.4&nbsp;



 <A HREF="decl.html#dcl.fct.def">dcl.fct.def</A>), it contains the
<TT>extern</TT> specifier (7.1.1&nbsp;



 <A HREF="dcl.html#dcl.stc">dcl.stc</A>) or
a <I>linkage-specification</I>
[Footnote: Appearing inside the braced-enclosed
<I>declaration-seq</I> in a <I>linkage-specification</I> does not
affect whether a declaration is a definition.  --- end
footnote]
(7.5&nbsp;



 <A HREF="dcl.html#dcl.link">dcl.link</A>) and neither an
<I>initializer</I> nor a <I>function-body</I>, it declares a static
data member in a class <S>declaration</S>
<B>definition</B>
(9.4&nbsp;



 <A HREF="class.html#class.static">class.static</A>), it is a class name
declaration (9.1&nbsp;



 <A HREF="class.html#class.name">class.name</A>), or it is
a <TT>typedef</TT> declaration
(7.1.3&nbsp;



 <A HREF="dcl.html#dcl.typedef">dcl.typedef</A>), a
<I>using-declaration</I>
(7.3.3&nbsp;



 <A HREF="dcl.html#namespace.udecl">namespace.udecl</A>), or a
<I>using-directive</I>
(7.3.4&nbsp;



 <A HREF="dcl.html#namespace.udir">namespace.udir</A>).
</BLOCKQUOTE>

<P>
Replace in 7.1.2&nbsp;



 <A HREF="dcl.html#dcl.fct.spec">dcl.fct.spec</A> paragraphs 5 and 6</P>

<BLOCKQUOTE>
<P>The <TT>virtual</TT> specifier shall only be used in declarations of
nonstatic class member functions that appear within a
<I>member-specification</I> of a class <S>declaration</S>
<B>definition</B>; see
10.3&nbsp;



 <A HREF="derived.html#class.virtual">class.virtual</A>.</P>
<P>
The <TT>explicit</TT> specifier shall be used only in declarations of
constructors within a class <S>declaration</S>
<B>definition</B>; see
12.3.1&nbsp;



 <A HREF="special.html#class.conv.ctor">class.conv.ctor</A>.</P>
</BLOCKQUOTE>

<P>
Replace in 7.1.3&nbsp;



 <A HREF="dcl.html#dcl.typedef">dcl.typedef</A> paragraph 4</P>

<BLOCKQUOTE>
A
<I>typedef-name</I>
that names a class is a
<I>class-name</I>
(9.1&nbsp;



 <A HREF="class.html#class.name">class.name</A>).
If a <I>typedef-name</I> is used following the <I>class-key</I>
in an <I>elaborated-type-specifier</I>
(7.1.5.3&nbsp;



 <A HREF="dcl.html#dcl.type.elab">dcl.type.elab</A>) or in the
<I>class-head</I>
of a class <S>declaration</S> <B>definition</B>
(9&nbsp;



 <A HREF="class.html#class">class</A>),
or is used as the <I>identifier</I> in the declarator for a
constructor or destructor declaration
(12.1&nbsp;



 <A HREF="special.html#class.ctor">class.ctor</A>,
12.4&nbsp;



 <A HREF="special.html#class.dtor">class.dtor</A>), the program is ill-formed.
</BLOCKQUOTE>

<P>
Replace in 7.3.1.2&nbsp;



 <A HREF="dcl.html#namespace.memdef">namespace.memdef</A> paragraph 3</P>

<BLOCKQUOTE>
The name of the friend is not found by simple name lookup until a
matching declaration is provided in that namespace scope (either
before or after the class <S>declaration</S>
<B>definition</B> granting friendship).
</BLOCKQUOTE>

<P>
Replace in 8.3.2&nbsp;



 <A HREF="decl.html#dcl.ref">dcl.ref</A> paragraph 4</P>

<BLOCKQUOTE>
There shall be no references to references, no arrays of references,
and no pointers to references.  The declaration of a reference shall
contain an <I>initializer</I>
(8.5.3&nbsp;



 <A HREF="decl.html#dcl.init.ref">dcl.init.ref</A>) except when
the declaration contains an explicit <TT>extern</TT> specifier
(7.1.1&nbsp;



 <A HREF="dcl.html#dcl.stc">dcl.stc</A>), is a class member
(9.2&nbsp;



 <A HREF="class.html#class.mem">class.mem</A>) declaration within a
class <S>declaration</S> <B>definition</B>, or is the
declaration of a parameter or a return type
(8.3.5&nbsp;



 <A HREF="decl.html#dcl.fct">dcl.fct</A>); see
3.1&nbsp;



 <A HREF="basic.html#basic.def">basic.def</A>.
</BLOCKQUOTE>

<P>
Replace in 8.5.3&nbsp;



 <A HREF="decl.html#dcl.init.ref">dcl.init.ref</A> paragraph 3</P>
<BLOCKQUOTE>
The initializer can be omitted for a reference only in a parameter
declaration (8.3.5&nbsp;



 <A HREF="decl.html#dcl.fct">dcl.fct</A>), in the
declaration of a function return type, in the declaration of a class
member within its class <S>declaration</S> <B>definition</B>
(9.2&nbsp;



 <A HREF="class.html#class.mem">class.mem</A>), and where the
<TT>extern</TT> specifier is explicitly used.
</BLOCKQUOTE>

<P>
Replace in 9.1&nbsp;



 <A HREF="class.html#class.name">class.name</A> paragraph 2</P>
<BLOCKQUOTE>
A class <S>definition</S> <B>declaration</B> introduces the
class name into the scope where it is <S>defined</S>
<B>declared</B> and hides any class, object, function, or other
declaration of that name in an enclosing scope
(3.3&nbsp;



 <A HREF="basic.html#basic.scope">basic.scope</A>).  If a class name
is declared in a scope where an object, function, or enumerator of the
same name is also declared, then when both declarations are in scope,
the class can be referred to only using an
<I>elaborated-type-specifier</I>
(3.4.4&nbsp;



 <A HREF="basic.html#basic.lookup.elab">basic.lookup.elab</A>).
</BLOCKQUOTE>

<P>
Replace in 9.4&nbsp;



 <A HREF="class.html#class.static">class.static</A> paragraph 4</P>
<BLOCKQUOTE>
Static members obey the usual class member access rules (clause
11&nbsp;



 <A HREF="access.html#class.access">class.access</A>).  When used
in the declaration of a class member, the <TT>static</TT> specifier
shall only be used in the member declarations that appear within the
<I>member-specification</I> of the class <S>declaration</S>
<B>definition</B>.
</BLOCKQUOTE>

<P>Replace in 9.7&nbsp;



 <A HREF="class.html#class.nest">class.nest</A> paragraph 1</P>
<BLOCKQUOTE>
A class can be <S>defined</S> <B>declared</B> within another
class.  A class <S>defined</S> <B>declared</B> within
another is called a <I>nested</I> class.  The name of a nested class
is local to its enclosing class.  The nested class is in the scope of
its enclosing class.  Except by using explicit pointers, references,
and object names, declarations in a nested class can use only type
names, static members, and enumerators from the enclosing class.
</BLOCKQUOTE>

<P>
Replace in 9.8&nbsp;



 <A HREF="class.html#class.local">class.local</A> paragraph 1</P>
<BLOCKQUOTE>
A class can be <S>defined</S> <B>declared</B> within a
function definition; such a class is called a <I>local</I> class.  The
name of a local class is local to its enclosing scope.  The local
class is in the scope of the enclosing scope, and has the same access
to names outside the function as does the enclosing function.
Declarations in a local class can use only type names, static
variables, <TT>extern</TT> variables and functions, and enumerators
from the enclosing scope.
</BLOCKQUOTE>

<P>
Replace in 10&nbsp;



 <A HREF="derived.html#class.derived">class.derived</A> paragraph 1</P>
<BLOCKQUOTE>
... The <I>class-name</I> in a <I>base-specifier</I> shall not be an
incompletely defined class (clause 9&nbsp;



 <A HREF="class.html#class">class</A>);
this class is called a
<I>direct</I> <I>base</I> <I>class</I> for the class being
<S>declared</S> <B>defined</B>.  During the lookup for a
base class name, non-type names are ignored
(3.3.7&nbsp;



 <A HREF="basic.html#basic.scope.hiding">basic.scope.hiding</A>).  
If the name found is not a <I>class-name</I>, the program is ill-formed.
A class <TT>B</TT> is a base class of a class <TT>D</TT> if it is a
direct base class of <TT>D</TT> or a direct base class of one of
<TT>D</TT>'s base classes.  A class is an <I>indirect</I> base class
of another if it is a base class but not a direct base class.  A class
is said to be (directly or indirectly) <I>derived</I> from its (direct
or indirect) base classes.  [<I>Note:</I> See clause
11&nbsp;



 <A HREF="access.html#class.access">class.access</A>
for the meaning of <I>access-specifier</I>.]  Unless
<S>redefined</S> <B>redeclared</B> in the
derived class, members of a base class are also considered to be
members of the derived class.  The base class members are said to be
<I>inherited</I> by the derived class.  Inherited members can be
referred to in expressions in the same manner as other members of the
derived class, unless their names are hidden or ambiguous
(10.2&nbsp;



 <A HREF="derived.html#class.member.lookup">class.member.lookup</A>).
[<I>Note:</I> the scope resolution operator <TT>::</TT>
(5.1&nbsp;



 <A HREF="expr.html#expr.prim">expr.prim</A>)
can be used to refer to a direct or indirect base member explicitly.
This allows access to a name that has been <S>redefined</S>
<B>redeclared</B> in the derived class.  A derived class can itself
serve as a base class subject to access control; see
11.2&nbsp;



 <A HREF="access.html#class.access.base">class.access.base</A>.  
A pointer to a derived class can be implicitly converted to a pointer
to an accessible unambiguous base class
(4.10&nbsp;



 <A HREF="conv.html#conv.ptr">conv.ptr</A>).
An lvalue of a derived class type can be bound to a reference to an
accessible unambiguous base class
(8.5.3&nbsp;



 <A HREF="decl.html#dcl.init.ref">dcl.init.ref</A>).]
</BLOCKQUOTE>

<P>
Replace in 10.1&nbsp;



 <A HREF="derived.html#class.mi">class.mi</A> paragraph 5</P>
<BLOCKQUOTE>
For another example,
<BLOCKQUOTE>
<TT>
<PRE>
class V { /* ... */ };
class A : virtual public V { /* ... */ };
class B : virtual public V { /* ... */ };
class C : public A, public B { /* ... */ };
</PRE>
</TT>
</BLOCKQUOTE>
for an object <TT>c</TT> of class type <TT>C</TT>, a single subobject
of type <TT>V</TT> is shared by every base subobject of <TT>c</TT>
that <S>is declared to have</S> <B>has</B> a
<TT>virtual</TT> base class of type <TT>V</TT>.
</BLOCKQUOTE>

<P>
Replace in the example in 10.2&nbsp;



 <A HREF="derived.html#class.member.lookup">class.member.lookup</A>
paragraph 6 (the whole paragraph was turned into a note by the
resolution of <A HREF="
     cwg_defects.html#39">core issue 39</A>)</P>
<BLOCKQUOTE>
The names <S>defined</S> <B>declared</B> in <TT>V</TT> and
the left hand instance of <TT>W</TT> are hidden by those in
<TT>B</TT>, but the names <S>defined</S> <B>declared</B> in
the right hand instance of <TT>W</TT> are not hidden at all.
</BLOCKQUOTE>

<P>
Replace in 10.4&nbsp;



 <A HREF="derived.html#class.abstract">class.abstract</A> paragraph 2</P>
<BLOCKQUOTE>
... A virtual function is specified <I>pure</I> by using a
<I>pure-specifier</I> (9.2&nbsp;



 <A HREF="class.html#class.mem">class.mem</A>)
in the function declaration in the class <S>declaration</S>
<B>definition</B>. ...
</BLOCKQUOTE>

<P>
Replace in the footnote at the end of 11.2&nbsp;



 <A HREF="access.html#class.access.base">class.access.base</A>
paragraph 1</P>
<BLOCKQUOTE>
[Footnote: As specified previously in clause
11&nbsp;



 <A HREF="access.html#class.access">class.access</A>, private members of
a base class remain inaccessible even to derived classes unless
<TT>friend</TT> declarations within the base class
<S>declaration</S> <B>definition</B> are used to grant access
explicitly.]
</BLOCKQUOTE>

<P>
Replace in 11.3&nbsp;



 <A HREF="access.html#class.access.dcl">class.access.dcl</A> paragraph 1</P>
<BLOCKQUOTE>
The access of a member of a base class can be changed in the derived
class by mentioning its <I>qualified-id</I> in the derived class
<S>declaration</S> <B>definition</B>.  Such mention is
called an <I>access</I> <I>declaration</I>. ...
</BLOCKQUOTE>

<P>
Replace in the example in 13.4&nbsp;



 <A HREF="over.html#over.over">over.over</A> paragraph 5</P>
<BLOCKQUOTE>
The initialization of <TT>pfe</TT> is ill-formed because no
<TT>f()</TT> with type <TT>int(...)</TT> has been
<S>defined</S> <B>declared</B>, and not because of any
ambiguity.
</BLOCKQUOTE>

<P>
Replace in C.1.5&nbsp;



 <A HREF="diff.html#diff.dcl">diff.dcl</A> paragraph 1</P>
<BLOCKQUOTE>
<B>Rationale:</B> Storage class specifiers don't have any meaning when
associated with a type.  In C++, class members can be
<S>defined</S> <B>declared</B> with the <TT>static</TT>
storage class specifier.  Allowing storage class specifiers on type
declarations could render the code confusing for users.
</BLOCKQUOTE>

<P>
Replace in C.1.7&nbsp;



 <A HREF="diff.html#diff.class">diff.class</A> paragraph 3</P>
<BLOCKQUOTE>
In C++, a typedef name may not be <S>redefined</S> <B>redeclared</B> in a class
<S>declaration</S> <B>definition</B> after being used in <S>the
declaration</S> <B>that definition</B>
</BLOCKQUOTE>

<I>Drafting notes:</I>
<P>
The resolution of <A HREF="
     cwg_defects.html#45">core issue 45</A> (DR)
deletes 11.8&nbsp;



 <A HREF="access.html#class.access.nest">class.access.nest</A> paragraph 2.</P>

<P>
The following occurrences of "class declaration" are not changed:</P>
<UL>
<LI>5.3.4&nbsp;



 <A HREF="expr.html#expr.new">expr.new</A> paragraph 4
</LI>

<LI>7.1.3&nbsp;



 <A HREF="dcl.html#dcl.typedef">dcl.typedef</A> paragraph 1
</LI>

<LI>9.1&nbsp;



 <A HREF="class.html#class.name">class.name</A> paragraphs 3 and 4
</LI>

<LI>11.4&nbsp;



 <A HREF="access.html#class.friend">class.friend</A> paragraph 9
</LI>

<LI>C.1.7&nbsp;



 <A HREF="diff.html#diff.class">diff.class</A> paragraph 1
</LI>

</UL>

<BR>
<BR>
<HR>
<A NAME="383"></A>
<H4>383.
  
Is a class with a declared but not defined destructor a POD?
</H4>
<B>Section: </B>9&nbsp;



 <A HREF="class.html#class">class</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Gennaro Prota
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>18 Sep 2002<BR>


<P>[Voted into WP at March 2004 meeting.]</P>

<P>The standard (9&nbsp;



 <A HREF="class.html#class">class</A> par. 4) says that
"A POD-struct is an aggregate class
that has no non-static data members of type non-POD-struct,
non-POD-union (or array of such types) or reference, and has no
user-defined copy assignment operator and no user-defined destructor."</P>

<P>Note that it says 'user-defined', not 'user-declared'. Is it the
intent that if e.g. a copy assignment operator is declared but not
defined, this does not (per se) prevent the class to be a POD-struct?</P>

<P>
<B>Proposed resolution (April 2003):</B>
</P>

<P>
Replace in 9&nbsp;



 <A HREF="class.html#class">class</A> paragraph 4</P>

<BLOCKQUOTE>
A <I>POD-struct</I> is an aggregate class that has no non-static data
members of type non-POD-struct, non-POD-union (or array of such types)
or reference, and has no user-<S>defined</S> <B>declared</B>
copy assignment operator and no user-<S>defined</S>
<B>declared</B> destructor.  Similarly, a <I>POD-union</I> is an
aggregate union that has no non-static data members of type
non-POD-struct, non-POD-union (or array of such types) or reference,
and has no user-<S>defined</S> <B>declared</B> copy
assignment operator and no user-<S>defined</S>
<B>declared</B> destructor.
</BLOCKQUOTE>

<P>
<I>Drafting note: The changes are shown relative to TC1, incorporating
the changes from the resolution of
<A HREF="
     cwg_defects.html#148">core issue 148</A>.</I>
</P>

<BR>
<BR>
<HR>
<A NAME="417"></A>
<H4>417.
  
Using derived-class qualified name in out-of-class nested class definition
</H4>
<B>Section: </B>9.1&nbsp;



 <A HREF="class.html#class.name">class.name</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Jon Caves
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>19 May 2003<BR>


<P>[Voted into WP at October 2004 meeting.]</P>

<P>We had a user complain that our compiler was allowing the
following code:</P>
<PRE>
  struct B {
    struct S;
  };

  struct D : B { };

  struct D::S {
  };
</PRE>

<P>We took one look at the code and made the reasonable (I would claim)
assumption that this was
indeed a bug in our compiler. Especially as we had just fixed a very
similar issue with the
definition of static data members.</P>

<P>Imagine our surprise when code like this showed up in Boost and that
every other compiler we tested accepts this code. So is this
indeed legal (it seems like
it must be) and if so is there any justification for this beyond
3.4.3.1&nbsp;



 <A HREF="basic.html#class.qual">class.qual</A>?</P>

<P>
<U>John Spicer:</U>
The equivalent case for a member function is covered by the declarator
rules in 8.3&nbsp;



 <A HREF="decl.html#dcl.meaning">dcl.meaning</A> paragraph 1.  The committee has
previously run into cases where a restriction should apply to both
classes and non-classes, but fails to do so because there is no 
equivalent of 8.3&nbsp;



 <A HREF="decl.html#dcl.meaning">dcl.meaning</A> paragraph 1 for classes.</P>

<P>Given that, by the letter of the standard, I would say that this
case is allowed.</P>

<P>
<B>Notes from October 2003 meeting:</B>
</P>

<P>We feel this case should get an error.</P>

<P>
<B>Proposed Resolution (October 2003):</B>
</P>

<P>Note that the change here interacts with
<A HREF="
     cwg_defects.html#432">issue 432</A>.</P>

<P>Add the following as a new paragraph immediately following
3.3.1&nbsp;



 <A HREF="basic.html#basic.scope.pdecl">basic.scope.pdecl</A> paragraph 2:</P>
<BLOCKQUOTE>
The point of declaration for a class first declared by a
<I>class-specifier</I> is 
immediately after the <I>identifier</I>
or <I>template-id</I> (if any) in its <I>class-head</I>
(Clause 9&nbsp;



 <A HREF="class.html#class">class</A>). 
The point of declaration for an enumeration is immediately after
the <I>identifier</I> (if any) in its <I>enum-specifier</I>
(7.2&nbsp;



 <A HREF="dcl.html#dcl.enum">dcl.enum</A>). 
</BLOCKQUOTE>

<P>Change point 1 of 3.3.6&nbsp;



 <A HREF="basic.html#basic.scope.class">basic.scope.class</A> paragraph 1 to read: </P>
<BLOCKQUOTE>
The potential scope of a name declared in a class consists not only of the 
declarative region following the name's
<S>declarator</S> <B>point of declaration</B>, but also 
of all function bodies, default arguments, and constructor
<I>ctor-initializer</I>s in that 
class (including such things in nested classes). 
</BLOCKQUOTE>

<P>
<I>[Note that the preceding change duplicates one of the changes
in the proposed resolution of issue 432.]</I>
</P>

<P>Change 14.7.2&nbsp;



 <A HREF="template.html#temp.explicit">temp.explicit</A> paragraph 2 to read: </P>
<BLOCKQUOTE>
If the explicit instantiation is for a member function, a member
class or a static 
data member of a class template specialization, the name of
the class template 
specialization in the <I>qualified-id</I> for the member <S>declarator</S>
<B>name</B> shall be a <I>template-id</I>.
</BLOCKQUOTE>

<P>Add the following as paragraph 5 of Clause 9&nbsp;



 <A HREF="class.html#class">class</A>:</P>
<BLOCKQUOTE> 
If a <I>class-head</I> contains a <I>nested-name-specifier</I>,
the <I>class-specifier</I> shall refer to a 
class that was previously declared directly in the class or namespace
to which the <I>nested-name-specifier</I> refers (i.e., neither
inherited nor introduced by a <I>using-declaration</I>), 
and the <I>class-specifier</I> shall appear in a namespace enclosing the 
previous declaration. 
</BLOCKQUOTE>

<P>Delete 9.1&nbsp;



 <A HREF="class.html#class.name">class.name</A> paragraph 4 (this was added
by <A HREF="
     cwg_defects.html#284">issue 284</A>):</P>
<BLOCKQUOTE>
When a <I>nested-name-specifier</I> is specified in a
<I>class-head</I> or in an
<I>elaborated-type-specifier</I>, the resulting qualified name
shall refer to a previously declared member of the class or namespace to
which the <I>nested-name-specifier</I> refers, and
the member shall not have been introduced by a
using-declaration in the scope of the class or namespace
nominated by the <I>nested-name-specifier</I>.
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="328"></A>
<H4>328.
  
Missing requirement that class member types be complete
</H4>
<B>Section: </B>9.2&nbsp;



 <A HREF="class.html#class.mem">class.mem</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Michiel Salters
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>10 Dec 2001<BR>


<P>[Voted into WP at March 2004 meeting.]</P>

<P>Is it legal to use an incomplete type (3.9&nbsp;



 <A HREF="basic.html#basic.types">basic.types</A>
paragraph 6) as a
class member, if no object of such class is ever created ?</P>

<P>And as a class template member, even if the template is instantiated,
but no object of the instantiated class is created?</P>

<P>The consensus seems to be NO, but no wording was found in the standard
which explicitly disallows it.</P>

<P>The problem seems to be that most of the restrictions on incomplete types
are on their use in objects, but class members are not objects.</P>

<P>A possible resolution, if this is considered a defect, is to add to 
3.2&nbsp;



 <A HREF="basic.html#basic.def.odr">basic.def.odr</A> paragraph 4, (situations when T must be complete),
the use of T as a member of a class or instantiated class template.</P>

<P>The thread on comp.std.c++ which brought up the issue was 
"Compiler differences: which is correct?", started 2001 11 30.
&lt;3c07c8fb$0$8507$ed9e5944@reading.news.pipex.net&gt;</P>

<P>
<B>Proposed Resolution (April 2002, revised April 2003):</B>
</P>

<P>Change the first bullet of the note in 3.2&nbsp;



 <A HREF="basic.html#basic.def.odr">basic.def.odr</A>
paragraph 4 and add two new bullets following it, as follows:</P>
<UL>
<LI>an object of type <TT>T</TT> is defined
(3.1&nbsp;



 <A HREF="basic.html#basic.def">basic.def</A><S>, 5.3.4&nbsp;



 <A HREF="expr.html#expr.new">expr.new</A></S>), or</LI>
<LI>a non-static class data member of type <TT>T</TT> is declared
(9.2&nbsp;



 <A HREF="class.html#class.mem">class.mem</A>), or</LI>
<LI>
<TT>T</TT> is used as the object type or array element type
in a <I>new-expression</I> (5.3.4&nbsp;



 <A HREF="expr.html#expr.new">expr.new</A>), or</LI>
</UL>

<P>
Replace 9.2&nbsp;



 <A HREF="class.html#class.mem">class.mem</A> paragraph 8 by:</P>
<BLOCKQUOTE>
Non-<TT>static</TT> (9.4&nbsp;



 <A HREF="class.html#class.static">class.static</A>) data members shall
not have incomplete types.
In particular, a class <TT>C</TT> shall not contain a non-<TT>static</TT>
member of class <TT>C</TT>, but it can contain a pointer or reference to
an object of class <TT>C</TT>.
</BLOCKQUOTE>

<P>See also 3.9&nbsp;



 <A HREF="basic.html#basic.types">basic.types</A> paragraph 6, which is relevant
but not changed by the Proposed Resolution.</P>

<BR>
<BR>
<HR>
<A NAME="437"></A>
<H4>437.
  
Is type of class allowed in member function exception specification?
</H4>
<B>Section: </B>9.2&nbsp;



 <A HREF="class.html#class.mem">class.mem</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Cary Coutant
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>10 Oct 2003<BR>


<P>[Voted into WP at April 2005 meeting.]</P>

<P>I've encountered a C++ program in which a member function wants to 
declare that it may throw an object of its own class, e.g.:</P>
<PRE>
  class Foo {
  private:
     int val;
  public:
     Foo( int &amp;initval ) { val = initval; };
     void throwit() throw(Foo) { throw (*this); };
  };
</PRE>
<P>The compiler is complaining that Foo is an incomplete type, and can't be 
used in the exception specification.</P>

<P>My reading of the standard [basic.types] is inconclusive.  Although it 
does state that the class declaration is considered complete when the 
closing brace is read, I believe it also intends that the member 
function declarations should not be semantically validated until the 
class has been completely declared.</P>

<P>If this isn't allowed, I don't know how else a member function could be 
declared to throw an object of its own class.</P>

<P>
<U>John Spicer</U>:
The type is considered complete within function bodies, but not in their 
declaration (see 9.2&nbsp;



 <A HREF="class.html#class.mem">class.mem</A> paragraph 2).</P>

<P>
<B>Proposed Resolution:</B>
</P>

<P>Change 9.2&nbsp;



 <A HREF="class.html#class.mem">class.mem</A> paragraph 2 as follows:</P>
<BLOCKQUOTE>
Within the class <I>member-specification</I>, the class is regarded
as complete within function bodies, default arguments<B>,
<I>exception-specification</I>s,</B> and constructor
<I>ctor-initializer</I>s (including such things in nested classes).
</BLOCKQUOTE>

<P>
<B>Rationale:</B> Taken with 8.3.5&nbsp;



 <A HREF="decl.html#dcl.fct">dcl.fct</A> paragraph 6, the
<I>exception-specification</I> is the <I>only</I> part of a function
declaration/definition in which the class name cannot be used because
of its putative incompleteness.  There is no justification for
singling out exception specifications this way; both in the function
body and in a <TT>catch</TT> clause, the class type will be complete,
so there is no harm in allowing the class name to be used in the
<I>exception-specification</I>.
</P>

<BR>
<BR>
<HR>
<A NAME="406"></A>
<H4>406.
  
Static data member in class with name for linkage purposes
</H4>
<B>Section: </B>9.4.2&nbsp;



 <A HREF="class.html#class.static.data">class.static.data</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Jorgen Bundgaard
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>12 Mar 2003<BR>


<P>[Voted into WP at March 2004 meeting.]</P>

<P> The following test program is claimed to be a negative C++ 
test case for "Unnamed classes shall not contain static data members", 
c.f. ISO/IEC 14882 section 9.4.2&nbsp;



 <A HREF="class.html#class.static.data">class.static.data</A> paragraph 5.</P>

<PRE> 
  struct B {
         typedef struct {
                 static int i;          // Is this legal C++ ?
         } A;
  };
 
  int B::A::i = 47;      // Is this legal C++ ?
</PRE>
 
<P> We are not quite sure about what an "unnamed class" is. 
There is no exact definition in ISO/IEC 14882; the closest we can come to a 
hint is the wording of section 7.1.3&nbsp;



 <A HREF="dcl.html#dcl.typedef">dcl.typedef</A>
paragraph 5, where it seems to be understood that a class-specifier with no
identifier between "class" and "{" is unnamed. The identifier provided after
"}" ( "A" in the test case above) is there for "linkage purposes" only.</P>
 
<P>To us, class B::A in the test program above seems "named" 
enough, and there is certainly a mechanism to provide the definition for
B::A::i (in contrast to the note in section 9.4.2&nbsp;



 <A HREF="class.html#class.static.data">class.static.data</A>
paragraph 5).</P>
 
<P>Our position is therefore that the above test program is 
indeed legal C++. Can you confirm or reject this claim?</P>

<P>
<U>Herb Sutter replied to the submitter as follows:</U>
Here are my notes based on a grep for
"unnamed class" in the standard:</P>
<UL>
<LI>
3.5&nbsp;



 <A HREF="basic.html#basic.link">basic.link</A> paragraph 4, bullet 3, makes a note that
does not directly speak to your question but which draws the same distinction:
<BLOCKQUOTE>
a named class (clause class), or an unnamed class defined in a
typedef declaration in which the class has the typedef name for
linkage purposes (7.1.3&nbsp;



 <A HREF="dcl.html#dcl.typedef">dcl.typedef</A>);
</BLOCKQUOTE>
Likewise in your example, you have an unnamed class defined in a
typedef declaration.
</LI>
<LI>
9.4.2&nbsp;



 <A HREF="class.html#class.static.data">class.static.data</A> paragraph 5 does indeed appear to
me to make your example not supported by ISO C++ (although implementations
could allow it as an extension, and many implementation do happen to allow it).
</LI>
<LI>
7.1.3&nbsp;



 <A HREF="dcl.html#dcl.typedef">dcl.typedef</A> paragraph 5 does indeed likewise confirm
the interpretation you give of an unnamed class.
</LI>
</UL>

<P>So yes, an unnamed class is one where there is no identifier (class
name) between the class-key and the {. This is also in harmony with the
production for class-name in 9&nbsp;



 <A HREF="class.html#class">class</A> paragraph 1:</P>

<UL>
<I>class-name</I><TT>:</TT>
<UL>
<I>identifier</I>
<BR>
    <I>template-id</I>
</UL>
</UL>

<P>
<B>Notes from the October 2003 meeting:</B>
</P>

<P>We agree that the example is not valid; this is an unnamed class.
We will add wording to define an unnamed class.  The note in
9.4.2&nbsp;



 <A HREF="class.html#class.static.data">class.static.data</A> paragraph 5 should be corrected
or deleted.</P>

<P>
<B>Proposed Resolution (October 2003):</B>
</P>

<P>
At the end of clause 9&nbsp;



 <A HREF="class.html#class">class</A>,
paragraph 1, add the following:</P>

<BLOCKQUOTE>
A <I>class-specifier</I> where the <I>class-head</I> omits
the optional <I>identifier</I> defines an unnamed class.
</BLOCKQUOTE>

<P>
Delete the following from 9.4.2&nbsp;



 <A HREF="class.html#class.static.data">class.static.data</A> paragraph 5:</P>

<BLOCKQUOTE>
[ <I>Note:</I> this is because there is no mechanism to provide the
definitions for such static data members. ]
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="436"></A>
<H4>436.
  
Problem in example in 9.6 paragraph 4
</H4>
<B>Section: </B>9.6&nbsp;



 <A HREF="class.html#class.bit">class.bit</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Roberto Santos
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>10 October 2003<BR>


<P>[Voted into WP at October 2004 meeting.]</P>

<P>It looks like the example on 9.6&nbsp;



 <A HREF="class.html#class.bit">class.bit</A>
paragraph 4 has both the enum and function
contributing the identifier "f" for the same scope.</P>
<PRE>
  enum BOOL { f=0, t=1 };
  struct A {
    BOOL b:1;
  };
  A a;
  void f() {
    a.b = t;
    if (a.b == t) // shall yield true
    { /* ... */ }
  }
</PRE>

<P>
<B>Proposed resolution:</B>
</P>

<P>Change the example at the end of 9.6&nbsp;



 <A HREF="class.html#class.bit">class.bit</A>/4 from:</P>
<PRE>
  enum BOOL { f=0, t=1 };
  struct A {
    BOOL b:1;
  };
  A a;
  void f() {
    a.b = t;
    if (a.b == t) // shall yield true
    { /* ... */ }
  }

</PRE>
<P>To:</P>
<PRE>
  enum BOOL { FALSE=0, TRUE=1 };
  struct A {
    BOOL b:1;
  };
  A a;
  void f() {
    a.b = TRUE;
    if (a.b == TRUE) // shall yield true
    { /* ... */ }
  }

</PRE>

<BR>
<BR>
<HR>
<A NAME="198"></A>
<H4>198.
  
Definition of "use" in local and nested classes
</H4>
<B>Section: </B>9.8&nbsp;



 <A HREF="class.html#class.local">class.local</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Erwin Unruh
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>27 Jan 2000<BR>



<P>[Voted into WP at April 2003 meeting.]</P>



<P>9.8&nbsp;



 <A HREF="class.html#class.local">class.local</A>
 paragraph 1 says,</P>

<BLOCKQUOTE>
Declarations in a local class can use only type names, static
variables, <TT>extern</TT> variables and functions, and enumerators
from the enclosing scope.
</BLOCKQUOTE>

The definition of when an object or function is "used" is found in
3.2&nbsp;



 <A HREF="basic.html#basic.def.odr">basic.def.odr</A>
 paragraph 2 and
essentially says that the operands of <TT>sizeof</TT> and
non-polymorphic <TT>typeid</TT> operators are not used.  (The
resolution for <A HREF="
     cwg_defects.html#48">issue 48</A> will add
contexts in which integral constant expressions are required to the
list of non-uses.)

<P>This definition of "use" would presumably allow code like</P>

<PRE>
    void foo() {
        int i;
        struct S {
            int a[sizeof(i)];
        };
    };
</PRE>

which is required for C compatibility.

<P>However, the restrictions on nested classes in
9.7&nbsp;



 <A HREF="class.html#class.nest">class.nest</A>
 paragraph 1 are very
similar to those for local classes, and the example there explicitly
states that a reference in a <TT>sizeof</TT> expression is a forbidden
use (abbreviated for exposition):</P>

<PRE>
    class enclose {
    public:
        int x;
        class inner {
            void f(int i)
            {
                int a = sizeof(x);  // <I>error: refers to </I>enclose::x
            }
        };
    };
</PRE>

<P>[As a personal note, I have seen real-world code that was exactly like
this; it was hard to persuade the author that the required
writearound, <TT>sizeof(((enclose*) 0)-&gt;x)</TT>, was an improvement
over <TT>sizeof(x)</TT>. <I>&mdash;wmm</I>]</P>

<P>Similarly, 9.2&nbsp;



 <A HREF="class.html#class.mem">class.mem</A> paragraph 9 would appear to
prohibit examples like the following:</P>

<PRE>
    struct B {
        char x[10];
    };
    struct D: B {
        char y[sizeof(x)];
    };
</PRE>

<P>
<B>Suggested resolution:</B> Add cross-references to
3.2&nbsp;



 <A HREF="basic.html#basic.def.odr">basic.def.odr</A>
 following the word
"use" in both 9.7&nbsp;



 <A HREF="class.html#class.nest">class.nest</A>
 and
9.8&nbsp;



 <A HREF="class.html#class.local">class.local</A>
, and change the example
in 9.7&nbsp;



 <A HREF="class.html#class.nest">class.nest</A>
 to indicate that a
reference in a <TT>sizeof</TT> expression is permitted.  In
9.2&nbsp;



 <A HREF="class.html#class.mem">class.mem</A> paragraph 9, "referred to" should be
changed to "used" with a cross_reference to
3.2&nbsp;



 <A HREF="basic.html#basic.def.odr">basic.def.odr</A>.</P>

<P>
<B>Notes from 10/01 meeting:</B>
</P>

<P>It was noted that the suggested resolution did not make the
<TT>sizeof()</TT> example in 9.7&nbsp;



 <A HREF="class.html#class.nest">class.nest</A> valid.
Although the reference to the argument of <TT>sizeof()</TT> is not regarded
as a use, the right syntax must be used nonetheless to reference a non-static
member from the enclosing class. The use of the member name by itself is not
valid. The consensus within the core working group was that nothing should be
done about this case. It was later discovered that
9.4&nbsp;



 <A HREF="class.html#class.static">class.static</A> paragraph 3 states that</P>
<BLOCKQUOTE>
<P>The
definition of a <TT>static</TT>
member shall not use directly the names of the nonstatic members of its class
or of a base class of its class (including as operands of the <TT>sizeof</TT>
operator). The definition of a <TT>static</TT> member may only refer to
these members to
form pointer to members (5.3.1&nbsp;



 <A HREF="expr.html#expr.unary.op">expr.unary.op</A>) or
with the class member access syntax (5.2.5&nbsp;



 <A HREF="expr.html#expr.ref">expr.ref</A>).</P>
</BLOCKQUOTE>

<P>This seems to
reinforce the decision of the working group.</P>

<P>The use of "use" should still be cross-referenced. The
statements in 9.7&nbsp;



 <A HREF="class.html#class.nest">class.nest</A> and 9.8&nbsp;



 <A HREF="class.html#class.local">class.local</A>
should also be rewritten to state the requirement
positively rather than negatively as the list of "can't"s is already missing
some cases such as template parameters. </P>

<P>
<B>Notes from the 4/02 meeting:</B>
</P>

<P>We backed away from "use" in the technical sense, because the
requirements on the form of reference are the same whether or not
the reference occurs inside a <TT>sizeof</TT>.</P>

<P>
<B>Proposed Resolution (revised October 2002):</B>
</P>

<P>In 9.2&nbsp;



 <A HREF="class.html#class.mem">class.mem</A> paragraph 9, replace </P>
<BLOCKQUOTE>
  <P>Except when used to form a pointer to member
(5.3.1&nbsp;



 <A HREF="expr.html#expr.unary.op">expr.unary.op</A>), when used in the body of a
 nonstatic member function of 
  its class or of a class derived from its class
 (9.3.1&nbsp;



 <A HREF="class.html#class.mfct.nonstatic">class.mfct.nonstatic</A>), or when used in
 a <I>mem-initializer</I> for a 
  constructor for its class or for a class derived from its class
(12.6.2&nbsp;



 <A HREF="special.html#class.base.init">class.base.init</A>), a nonstatic data or function member
 of a class shall only be referred to with the class member access syntax
(5.2.5&nbsp;



 <A HREF="expr.html#expr.ref">expr.ref</A>).</P>
</BLOCKQUOTE>
<P>with the following paragraph</P>
<BLOCKQUOTE>
  <P>Each occurrence in an expression of the name of a nonstatic data 
  member or nonstatic member function of a class shall be expressed as a class 
  member access (5.2.5&nbsp;



 <A HREF="expr.html#expr.ref">expr.ref</A>), except when it appears
  in the formation of a pointer to member 
  (5.3.1&nbsp;



 <A HREF="expr.html#expr.unary.op">expr.unary.op</A>), when it appears in the body
  of a nonstatic member function 
  of its class or of a class derived from its class
(9.3.1&nbsp;



 <A HREF="class.html#class.mfct.nonstatic">class.mfct.nonstatic</A>), or when it appears in a
<I>mem-initializer</I> for 
  a constructor for its class or for a class derived from its class
(12.6.2&nbsp;



 <A HREF="special.html#class.base.init">class.base.init</A>).</P>
</BLOCKQUOTE>
<P>In 9.7&nbsp;



 <A HREF="class.html#class.nest">class.nest</A>
 paragraph 1, replace the last sentence,</P>
<BLOCKQUOTE>
  <P>Except by using explicit pointers, references, and object names, 
  declarations in a nested class can use only type names, static members, and 
  enumerators from the enclosing class.</P>
</BLOCKQUOTE>
<P>with the following</P>
<BLOCKQUOTE>
  <P>[Note: In accordance with 9.2&nbsp;



 <A HREF="class.html#class.mem">class.mem</A>,
  except by using explicit pointers, 
  references, and object names, declarations in a nested class shall not use
  nonstatic data members or nonstatic member functions from the 
  enclosing class. This restriction applies in all constructs including the 
  operands of the <TT>sizeof</TT> operator.]</P>
</BLOCKQUOTE>
<P>In the example following 9.7&nbsp;



 <A HREF="class.html#class.nest">class.nest</A>
paragraph 1, change the comment on the first statement of 
function <TT>f</TT> to emphasize that <TT>sizeof(x)</TT> is an error. The 
example reads in full:</P>
<PRE>
  int x;
  int y;
  class enclose {
  public:
    int x;
    static int s;
    class inner {
      void f(int i)
      {
        int a = sizeof(x);  // <I>error: direct use of</I> <TT>enclose::x</TT> <I>even in sizeof</I>
        x = i;              // <I>error: assign to </I><TT>enclose::x</TT>
        s = i;              // <I>OK: assign to </I><TT>enclose::s</TT>
        ::x = i;            // <I>OK: assign to global</I> <TT>x</TT>
        y = i;              // <I>OK: assign to global</I> <TT>y</TT>
      }
      void g(enclose* p, int i)
      {
        p-&gt;x = i;        // <I>OK: assign to</I> <TT>enclose::x</TT>
      }
    };
  };
   
  inner* p = 0;             // <I>error:</I> <TT>inner</TT><I> not in scope</I>
</PRE>

<BR>
<BR>
<HR>
<A NAME="39"></A>
<H4>39.
  
Conflicting ambiguity rules
</H4>
<B>Section: </B>10.2&nbsp;



 <A HREF="derived.html#class.member.lookup">class.member.lookup</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Neal M Gafter
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>20 Aug 1998<BR>



<P>[Voted into WP at April 2005 meeting.]</P>



<P>The ambiguity text in 10.2&nbsp;



 <A HREF="derived.html#class.member.lookup">class.member.lookup</A>

may not say what we intended. It makes the
following example ill-formed:</P>
<PRE>
    struct A {
        int x(int);
    };
    struct B: A {
        using A::x;
        float x(float);
    };
    
    int f(B* b) {
        b-&gt;x(3);  // ambiguous
    }
</PRE>
This is a name lookup ambiguity because of 10.2&nbsp;



 <A HREF="derived.html#class.member.lookup">class.member.lookup</A>
 paragraph 2:
<BLOCKQUOTE>... Each of these declarations that was introduced by a using-declaration
is considered to be from each sub-object of C that is of the type containing
the declaration designated by the using-declaration. If the resulting set
of declarations are not all from sub-objects of the same type, or the set
has a nonstatic member and includes members from distinct sub-objects,
there is an ambiguity and the program is ill-formed.</BLOCKQUOTE>
This contradicts the text and example in paragraph 12 of 7.3.3&nbsp;



 <A HREF="dcl.html#namespace.udecl">namespace.udecl</A>
.

<P>
<B>Proposed Resolution (10/00):</B>
</P>

<OL>

<LI>
<P>Replace the two cited sentences from 10.2&nbsp;



 <A HREF="derived.html#class.member.lookup">class.member.lookup</A>
paragraph 2 with the following:</P>

<BLOCKQUOTE>

The resulting set of declarations shall all be from sub-objects
of the same type, or there shall be a set of declarations from
sub-objects of a single type that contains <I>using-declaration</I>s
for the declarations found in all other sub-object types.
Furthermore, for nonstatic members, the resulting set of
declarations shall all be from a single sub-object, or there shall
be a set of declarations from a single sub-object that contains
<I>using-declarations</I> for the declarations found in all other
sub-objects.  Otherwise, there is an ambiguity and the program is
ill-formed.

</BLOCKQUOTE>

</LI>

<LI>
<P>Replace the examples in 10.2&nbsp;



 <A HREF="derived.html#class.member.lookup">class.member.lookup</A>
paragraph 3 with the following:</P>

<PRE>
    struct A {
        int x(int);
        static int y(int);
    };
    struct V {
        int z(int);
    };
    struct B: A, virtual V {
        using A::x;
        float x(float);
        using A::y;
        static float y(float);
        using V::z;
        float z(float);
    };
    struct C: B, A, virtual V {
    };

    void f(C* c) {
        c-&gt;x(3);    // ambiguous -- more than one sub-object A
        c-&gt;y(3);    // not ambiguous
        c-&gt;z(3);    // not ambiguous
    }
</PRE>

</LI>

</OL>

<P>
<B>Notes from 04/01 meeting:</B>
</P>

<P>The following example should be accepted but is rejected by
the wording above:</P>

<PRE>
    struct A { static void f(); };

    struct B1: virtual A {
        using A::f;
    };

    struct B2: virtual A {
        using A::f;
    };

    struct C: B1, B2 { };

    void g() {
        C::f();        // OK, calls A::f()
    }
</PRE>

<P>
<B>Notes from 10/01 meeting (Jason Merrill):</B>
</P>

<P>The example in the issues list:

<PRE>
    struct A {
        int x(int);
    };
    struct B: A {
        using A::x;
        float x(float);
    };
    
    int f(B* b) {
        b-&gt;x(3);  // ambiguous
    }
</PRE>

Is broken under the existing wording:

<BLOCKQUOTE>
... Each of these declarations that was introduced by a using-declaration
is considered to be from each sub-object of C that is of the type containing
the declaration designated by the using-declaration. If the resulting set
of declarations are not all from sub-objects of the same type, or the set
has a nonstatic member and includes members from distinct sub-objects,
there is an ambiguity and the program is ill-formed.</BLOCKQUOTE>

Since the two x's are considered to be "from" different objects, looking up
x produces a set including declarations "from" different objects, and the
program is ill-formed.  Clearly this is wrong.  The problem with the
existing wording is that it fails to consider lookup context.</P>

<P>The first proposed solution:

<BLOCKQUOTE>

The resulting set of declarations shall all be from sub-objects
of the same type, or there shall be a set of declarations from
sub-objects of a single type that contains <I>using-declaration</I>s
for the declarations found in all other sub-object types.
Furthermore, for nonstatic members, the resulting set of
declarations shall all be from a single sub-object, or there shall
be a set of declarations from a single sub-object that contains
<I>using-declarations</I> for the declarations found in all other
sub-objects.  Otherwise, there is an ambiguity and the program is
ill-formed.

</BLOCKQUOTE>

breaks this testcase:

<PRE>
    struct A { static void f(); };

    struct B1: virtual A {
        using A::f;
    };

    struct B2: virtual A {
        using A::f;
    };

    struct C: B1, B2 { };

    void g() {
        C::f();        // OK, calls A::f()
    }
</PRE>

because it considers the lookup context, but not the definition context;
under this definition of "from", the two declarations found are the
using-declarations, which are "from" B1 and B2.</P>

<P>The solution is to separate the notions of lookup and definition context.
I have taken an algorithmic approach to describing the strategy.</P>

<P>Incidentally, the earlier proposal allows one base to have a superset of
the declarations in another base; that was an extension, and my proposal
does not do that.  One algorithmic benefit of this limitation is to
simplify the case of a virtual base being hidden along one arm and not
another ("domination"); if we allowed supersets, we would need to remember
which subobjects had which declarations, while under the following
resolution we need only keep two lists, of subobjects and declarations.</P>

<P>
<B>Proposed resolution (October 2002):</B>
</P>

<P>Replace 10.2&nbsp;



 <A HREF="derived.html#class.member.lookup">class.member.lookup</A> paragraph 2 with: </P>
<BLOCKQUOTE>
<P>The following steps define the result of name lookup for a member
name f in a class scope C. </P>

<P>The <I>lookup set</I> for f in C, called S(f,C), consists of two
component sets: the <I>declaration set</I>, a set of members named f; and
the <I>subobject set</I>, a set of subobjects where declarations of these
members (possibly including using-declarations) were found.  In the
declaration set, using-declarations are replaced by the members they
designate, and type declarations (including injected-class-names) are
replaced by the types they designate.  S(f,C) is calculated as
follows. </P>

<P>If C contains a declaration of the name f, the declaration set contains
every declaration of f in C (excluding bases), the subobject set contains C
itself, and calculation is complete. </P>

<P>Otherwise, S(f,C) is initially empty. If C has base classes, calculate
the lookup set for f in each direct base class subjobject B<SUB>i</SUB>,
and merge each such lookup set S(f,B<SUB>i</SUB>) in turn into S(f,C). </P>

<P>The following steps define the result of merging lookup set
S(f,B<SUB>i</SUB>) into the intermediate S(f,C): </P>

<UL>
<LI>If each of the subobject members of S(f,B<SUB>i</SUB>) is a base
class subobject of at least one of the subobject members of S(f,C), S(f,C)
is unchanged and the merge is complete.  Conversely, if each of the
subobject members of S(f,C) is a base class subobject of at least one of
the subobject members of S(f,B<SUB>i</SUB>), the new S(f,C) is a copy of
S(f,B<SUB>i</SUB>).</LI>

<LI>Otherwise, if the declaration sets of S(f,B<SUB>i</SUB>) and S(f,C)
differ, the merge is ambiguous: the new S(f,C) is a lookup set with an
invalid declaration set and the union of the subobject sets. In subsequent
merges, an invalid declaration set is considered different from any
other.</LI>

<LI>Otherwise, consider each declaration d in the set, where d is a
member of class A.  If d is a nonstatic member, compare the A base class
subobjects of the subobject members of S(f,B<SUB>i</SUB>) and
S(f,C).  If they do not match, the merge is ambiguous, as in the
previous step.  [<I>Note:</I> It is not necessary to remember which A subobject
each member comes from, since using-declarations don't disambiguate. ]
</LI>

<LI> Otherwise, the new S(f,C) is a lookup set with the shared
set of declarations and the union of the subobject sets.</LI>
</UL>

<P>The result of name lookup for f in C is the declaration set of
S(f,C).  If it is an invalid set, the program is ill-formed. </P>

<P>[<I>Example:</I>
<PRE>
    struct A { int x; };                    // S(x,A) = {{ A::x }, { A }}
    struct B { float x; };                  // S(x,B) = {{ B::x }, { B }}
    struct C: public A, public B { };       // S(x,C) = { invalid, { A in C, B in C }}
    struct D: public virtual C { };         // S(x,D) = S(x,C)
    struct E: public virtual C { char x; }; // S(x,E) = {{ E::x }, { E }}
    struct F: public D, public E { };       // S(x,F) = S(x,E)

    int main() {
      F f;
      f.x = 0;   // OK, lookup finds { E::x }
    }
</PRE>

S(x,F) is unambiguous because the A and B base subobjects of D are also
base subobjects of E, so S(x,D) is discarded in the first merge step. --<I>end
example</I>]
</P>
</BLOCKQUOTE>

<P> Turn 10.2&nbsp;



 <A HREF="derived.html#class.member.lookup">class.member.lookup</A> paragraphs 5 and 6 into notes.</P>

<P>
<B>Notes from October 2003 meeting:</B>
</P>

<P>Mike Miller raised some new issues in N1543, and we adjusted the
proposed resolution as indicated in that paper.</P>

<P>
<B>Further information from Mike Miller (January 2004):</B>
</P>

<P>Unfortunately, I've become aware of a minor glitch in
the proposed resolution for issue 39 in N1543, so I'd like to
suggest a change that we can discuss in Sydney.</P>

<P>A brief review and background of the problem: the major change we
agreed on in Kona was to remove detection of multiple-subobject
ambiguity from class lookup (10.2&nbsp;



 <A HREF="derived.html#class.member.lookup">class.member.lookup</A>) and instead
handle it as part
of the class member access expression.  It was pointed out in
Kona that 11.2&nbsp;



 <A HREF="access.html#class.access.base">class.access.base</A>/5 has this effect:</P>
<BLOCKQUOTE>
    If a class member access operator, including an implicit
    "this-&gt;," is used to access a nonstatic data member or
    nonstatic member function, the reference is ill-formed if the
    left operand (considered as a pointer in the "." operator
    case) cannot be implicitly converted to a pointer to the
    naming class of the right operand.
</BLOCKQUOTE>
<P>After the meeting, however, I realized that this requirement is
not sufficient to handle all the cases.  Consider, for instance,</P>
<PRE>
    struct B {
        int i;
    };

    struct I1: B { };
    struct I2: B { };

    struct D: I1, I2 {
        void f() {
            i = 0;    // not ill-formed per 11.2p5
        }
    };
</PRE>
<P>Here, both the object expression ("this") and the naming class
are "D", so the reference to "i" satisfies the requirement in
11.2&nbsp;



 <A HREF="access.html#class.access.base">class.access.base</A>/5, even though it involves a
multiple-subobject ambiguity.</P>

<P>In order to address this problem, I proposed in N1543 to add a
paragraph following 5.2.5&nbsp;



 <A HREF="expr.html#expr.ref">expr.ref</A>/4:</P>
<BLOCKQUOTE>
    If E2 is a non-static data member or a non-static member
    function, the program is ill-formed if the class of E1 cannot
    be unambiguously converted (10.2) to the class of which E2 is
    directly a member.
</BLOCKQUOTE>
<P>That's not quite right.  It does diagnose the case above as
written; however, it breaks the case where qualification is used
to circumvent the ambiguity:</P>
<PRE>
    struct D2: I1, I2 {
        void f() {
            I2::i = 0;    // ill-formed per proposal
        }
    };
</PRE>
<P>In my proposed wording, the class of "this" can't be converted to
"B" (the qualifier is ignored), so the access is ill-formed.
Oops.</P>

<P>I think the following is a correct formulation, so the proposed
resolution we discuss in Sydney should contain the following
paragraph instead of the one in N1543:</P>
<BLOCKQUOTE>
    If E2 is a nonstatic data member or a non-static member
    function, the program is ill-formed if <B>the naming class
    (11.2) of E2</B> cannot be unambiguously converted (10.2) to
    the class of which E2 is directly a member.
</BLOCKQUOTE>
<P>This reformulation also has the advantage of pointing readers to
11.2&nbsp;



 <A HREF="access.html#class.access.base">class.access.base</A>, where the the convertibility requirement
from the class of
E1 to the naming class is located and which might otherwise be
overlooked.</P>

<P>
<B>Notes from the March 2004 meeting:</B>
</P>

<P>We discussed this further and agreed with these latest
recommendations.  Mike Miller has produced a paper N1626 that gives
just the final collected set of changes.</P>

<P>(This resolution also resolves <A HREF="
     cwg_defects.html#306">isssue 306</A>.)</P>

<BR>
<BR>
<HR>
<A NAME="306"></A>
<H4>306.
  
Ambiguity by class name injection
</H4>
<B>Section: </B>10.2&nbsp;



 <A HREF="derived.html#class.member.lookup">class.member.lookup</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Clark Nelson
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>19 Jul 2001<BR>


<P>[Voted into WP at April 2005 meeting.]</P>

<P>Is the following well-formed?
<PRE>
    struct A {
        struct B { };
    };
    struct C : public A, public A::B {
        B *p;
    };
</PRE>
The lookup of <TT>B</TT> finds both the struct <TT>B</TT> in <TT>A</TT>
and the injected <TT>B</TT> from the <TT>A::B</TT> base class.
Are they the same thing?  Does the standard say so?</P>

<P>What if a struct is found along one path and a typedef to that
struct is found along another path?  That should probably be valid,
but does the standard say so?</P>

<P>This is resolved by <A HREF="
     cwg_defects.html#39">issue 39</A>
</P>

<P>February 2004: Moved back to "Review" status because
<A HREF="
     cwg_defects.html#39">issue 39</A> was moved back to "Review".</P>
<BR>
<BR>
<HR>
<A NAME="390"></A>
<H4>390.
  
Pure virtual must be defined when implicitly called
</H4>
<B>Section: </B>10.4&nbsp;



 <A HREF="derived.html#class.abstract">class.abstract</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Daniel Frey
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>14 Nov 2002<BR>


<P>[Voted into WP at March 2004 meeting.]</P>

<P>In clause 10.4&nbsp;



 <A HREF="derived.html#class.abstract">class.abstract</A> paragraph 2, it reads:</P>
<BLOCKQUOTE>
A pure virtual function need be defined only if explicitly called with
the qualified-id syntax (5.1&nbsp;



 <A HREF="expr.html#expr.prim">expr.prim</A>).
</BLOCKQUOTE>

<P>This is IMHO incomplete. A dtor is a function (well, a "special member
function", but this also makes it a function, right?) but it is called
implicitly and thus without a qualified-id syntax. Another alternative
is that the pure virtual function is called directly or indirectly from
the ctor. Thus the above sentence which specifies when a pure virtual
function need be defined ("...only if...") needs to be extended:</P>
<BLOCKQUOTE>
A pure virtual function need be defined only if explicitly called with
the qualified-id syntax (5.1&nbsp;



 <A HREF="expr.html#expr.prim">expr.prim</A>) or if implicitly
called (12.4&nbsp;



 <A HREF="special.html#class.dtor">class.dtor</A> or 12.7&nbsp;



 <A HREF="special.html#class.cdtor">class.cdtor</A>).
</BLOCKQUOTE>

<P>
<B>Proposed resolution:</B>
</P>

<P>Change 10.4&nbsp;



 <A HREF="derived.html#class.abstract">class.abstract</A> paragraph 2 from</P>
<BLOCKQUOTE>
A pure virtual function need be defined only if explicitly called
with the <I>qualified-id</I> syntax (5.1&nbsp;



 <A HREF="expr.html#expr.prim">expr.prim</A>).
</BLOCKQUOTE>

<P>to</P>

<BLOCKQUOTE>
A pure virtual function need be defined only if
<S>explicitly</S> called with<B>, or as if with
(12.4&nbsp;



 <A HREF="special.html#class.dtor">class.dtor</A>),</B>
the <I>qualified-id</I> syntax (5.1&nbsp;



 <A HREF="expr.html#expr.prim">expr.prim</A>).
</BLOCKQUOTE>

<P>Note: 12.4&nbsp;



 <A HREF="special.html#class.dtor">class.dtor</A> paragraph 6 defines the "as if"
cited.</P>

<BR>
<BR>
<HR>
<A NAME="8"></A>
<H4>8.
  
Access to template arguments used in a function return type and in the nested name specifier
</H4>
<B>Section: </B>11&nbsp;



 <A HREF="access.html#class.access">class.access</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Ball
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>unknown<BR>



<P>[Moved to DR at 4/01 meeting.]</P>



<P>Consider the following example:</P>
<PRE>
    class A {
       class A1{};
       static void func(A1, int);
       static void func(float, int);
       static const int garbconst = 3;
     public:
       template &lt; class T, int i, void (*f)(T, int) &gt; class int_temp {};
       template&lt;&gt; class int_temp&lt;A1, 5, func&gt; { void func1() };
       friend int_temp&lt;A1, 5, func&gt;::func1();
       int_temp&lt;A1, 5, func&gt;* func2();
   };
   A::int_temp&lt;A::A1, A::garbconst + 2, &amp;A::func&gt;* A::func2() {...}
</PRE>
<B><U>ISSUE 1:</U></B>

<P>In 11&nbsp;



 <A HREF="access.html#class.access">class.access</A>
 paragraph 5 we have:
<UL>All access controls in clause 11 affect the ability to access a class
member name from a particular scope... In particular, access controls
apply as usual to member names accessed as part of a function return type,
even though it is not possible to determine the access privileges of that
use without first parsing the rest of the function declarator.</UL>
This means, if we take the loosest possible definition of "access from
a particular scope", that we have to save and check later the following
names</P>
<PRE>
      A::int_temp
      A::A1
      A::garbconst (part of an expression)
      A::func (after overloading is done)
</PRE>
I suspect that member templates were not really considered when this was
written, and that it might have been written rather differently if they
had been. Note that access to the template arguments is only legal because
the class has been declared a friend, which is probably not what most programmers
would expect.

<P>
<B>Rationale:</B>
</P>

<P>Not a defect. This behavior is as intended.</P>

<P>
<B><U>ISSUE 2:</U></B>
</P>

<P>Now consider <TT>void A::int_temp&lt;A::A1, A::garbconst + 2, &amp;A::func&gt;::func1()
{...}</TT> By my reading of 11.8&nbsp;



 <A HREF="access.html#class.access.nest">class.access.nest</A>
, the references to
<TT>A::A1</TT>, <TT>A::garbconst</TT> and <TT>A::func</TT> are now illegal,
and there is no way to define this function outside of the class. Is there
any need to do anything about either of these Issues?</P>

<P>
<B>Proposed resolution (04/01):</B>
</P>

<P>The resolution for this issue is contained in the resolution
for <A HREF="
     cwg_defects.html#45">issue 45</A>.</P>
<BR>
<BR>
<HR>
<A NAME="9"></A>
<H4>9.
  
Clarification of access to base class members
</H4>
<B>Section: </B>11.2&nbsp;



 <A HREF="access.html#class.access.base">class.access.base</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>unknown
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>unknown<BR>



<P>[Moved to DR at 4/01 meeting.]</P>



<P>11.2&nbsp;



 <A HREF="access.html#class.access.base">class.access.base</A>
 paragraph 4 says:</P>
<BLOCKQUOTE>A base class is said to be accessible if an invented public
member of the base class is accessible. If a base class is accessible,
one can implicitly convert a pointer to a derived class to a pointer to
that base class.</BLOCKQUOTE>
Given the above, is the following well-formed?
<PRE>
    class D;
     
    class B
    {
     protected:
       int b1;
 
       friend void foo( D* pd );
    };
     
    class D : protected B { };
     
    void foo( D* pd )
    {
       if ( pd-&gt;b1 &gt; 0 ); // Is 'b1' accessible?
    }
</PRE>
Can you access the protected member <TT>b1</TT> of <TT>B</TT> in <TT>foo</TT>?
Can you convert a <TT>D*</TT> to a <TT>B*</TT> in <TT>foo</TT>?

<P>
<U>1st interpretation:</U>
</P>

<P>A public member of <TT>B</TT> is accessible within <TT>foo</TT> (since
<TT>foo</TT> is a friend), therefore <TT>foo</TT> can refer to <TT>b1</TT> and convert
a <TT>D*</TT> to a <TT>B*</TT>.</P>

<P>
<U>2nd interpretation:</U>
</P>

<P>
<TT>B</TT> is a protected base class of <TT>D</TT>, and a public member of <TT>B</TT>
is a protected member of <TT>D</TT> and can only be accessed within members
of <TT>D</TT> and friends of <TT>D</TT>. Therefore <TT>foo</TT> cannot refer to
<TT>b1</TT> and cannot convert a <TT>D*</TT> to a <TT>B*</TT>.</P>

<P>(See J16/99-0042 = WG21 N1218.)</P>

<P>
<B>Proposed Resolution (04/01):</B>
</P>
<OL>
<LI>
Add preceding 11.2&nbsp;



 <A HREF="access.html#class.access.base">class.access.base</A>

paragraph 4:

<BLOCKQUOTE>
A base class <TT>B</TT> of <TT>N</TT> is <I>accessible</I> at <I>R</I>,
if
<UL>
<LI>
an invented public member of <TT>B</TT> would be a public member
of <TT>N</TT>, or</LI>
<LI>
<I>R</I> occurs in a member or friend of class <TT>N</TT>, and an
invented public member of <TT>B</TT> would be a private or protected
member of <TT>N</TT>, or</LI>
<LI>
<I>R</I> occurs in a member or friend of a class <TT>P</TT> derived
from <TT>N</TT>, and an invented public member of <TT>B</TT> would be
a private or protected member of <TT>P</TT>, or</LI>
<LI>
there exists a class <TT>S</TT> such that <TT>B</TT> is a base class
of <TT>S</TT> accessible at <I>R</I> and <TT>S</TT> is a base class
of <TT>N</TT> accessible at <I>R</I>. [<I>Example:</I>
<PRE>
    class B {
    public:
        int m;
    };

    class S: private B {
        friend class N;
    };

    class N: private S {
        void f() {
	    B* p = this;  // <I>OK because class S satisfies the</I>
			// <I>fourth condition above: B is a base</I>
			// <I>class of N accessible in f() because</I>
			// <I>B is an accessible base class of S</I>
			// <I>and S is an accessible base class of N.</I>
        }
    };
</PRE>
&mdash;<I>end example</I>]
</LI>
</UL>
</BLOCKQUOTE>
</LI>
<LI>
Delete the first sentence of
11.2&nbsp;



 <A HREF="access.html#class.access.base">class.access.base</A>
 paragraph 4:
<BLOCKQUOTE>
A base class is said to be accessible if an invented public member
of the base class is accessible.
</BLOCKQUOTE>
</LI>
<LI>
Replace the last sentence ("A member <I>m</I> is accessible...")
by the following:
<BLOCKQUOTE>
A member <TT>m</TT> is accessible at the point <I>R</I> when
named in class <TT>N</TT> if
<UL>
<LI>
<TT>m</TT> as a member of <TT>N</TT> is public, or</LI>
<LI>
<TT>m</TT> as a member of <TT>N</TT> is private, and <I>R</I>
occurs in a member or friend of class <TT>N</TT>, or</LI>
<LI>
<TT>m</TT> as a member of <TT>N</TT> is protected, and <I>R</I>
occurs in a member or friend of class <TT>N</TT>, or in a member
or friend of a class <TT>P</TT> derived from <TT>N</TT>, where
<TT>m</TT> as a member of <TT>P</TT> is private or protected, or</LI>
<LI>
there exists a base class <TT>B</TT> of <TT>N</TT> that is
accessible at <I>R</I>, and <TT>m</TT> is accessible at <I>R</I>
when named in class <TT>B</TT>. [<I>Example:</I>...
</LI>
</UL>
</BLOCKQUOTE>
</LI>
</OL>

<P>The resolution for <A HREF="
     cwg_defects.html#207">issue 207</A> modifies
this wording slightly.</P>

<BR>
<BR>
<HR>
<A NAME="16"></A>
<H4>16.
  
Access to members of indirect private base classes
</H4>
<B>Section: </B>11.2&nbsp;



 <A HREF="access.html#class.access.base">class.access.base</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>unknown
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>unknown<BR>



<P>[Moved to DR at 4/01 meeting.]</P>



<P>The text in 11.2&nbsp;



 <A HREF="access.html#class.access.base">class.access.base</A>

paragraph 4 does not seem to handle the following cases:</P>
<PRE>
    class D;
     
    class B {
    private:
        int i;
        friend class D;
    };
     
    class C : private B { };
     
    class D : private C {
        void f() {
            B::i; //1: well-formed?
            i;    //2: well-formed?
        }
    };
</PRE>
The member <TT>i</TT> is not a member of <TT>D</TT> and cannot be
accessed in the
scope of <TT>D</TT>. What is the naming class of the member
<TT>i</TT> on line <TT>//1</TT>
and <TT>line //2</TT>?

<P>
<B>Proposed Resolution (04/01):</B> The resolution for this issue
is contained in the resolution for <A HREF="
     cwg_defects.html#9">issue 9</A>..</P>
<BR>
<BR>
<HR>
<A NAME="207"></A>
<H4>207.
  
<I>using-declaration</I>s and protected access
</H4>
<B>Section: </B>11.2&nbsp;



 <A HREF="access.html#class.access.base">class.access.base</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Jason Merrill
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>28 Feb 2000<BR>


<P>[Moved to DR at 10/01 meeting.]</P>



<P>Consider the following example:</P>

<PRE>
  class A {
  protected:
    static void f() {};
  };

  class B : A {
  public:
    using A::f;
    void g() {
      A::f();
    }
  };
</PRE>

<P>The standard says in 11.2&nbsp;



 <A HREF="access.html#class.access.base">class.access.base</A> paragraph 4 that
the call to <TT>A::f</TT> is ill-formed:</P>

<BLOCKQUOTE>
A member <I>m</I> is accessible when named in class <I>N</I> if

<UL>
<LI>
<I>m</I> as a member of <I>N</I> is public, or</LI>

<LI>
<I>m</I> as a member of <I>N</I> is private, and the reference
occurs in a member or friend of class <I>N</I>, or</LI>

<LI>
<I>m</I> as a member of <I>N</I> is protected, and the reference
occurs in a member or friend of class <I>N</I>, or in a member or
friend of a class <I>P</I> derived from <I>N</I>, where <I>m</I> as a
member of <I>P</I> is private or protected, or</LI>

<LI>there exists a base class <I>B</I> of <I>N</I> that is accessible
at the point of reference, and <I>m</I> is accessible when named in
class <I>B</I>.</LI>

</UL>
</BLOCKQUOTE>

<P>Here, <I>m</I> is <TT>A::f</TT> and <I>N</I> is <TT>A</TT>.</P>

<UL>
<LI>
<TT>f</TT> as a member of <TT>A</TT> is public?  <B>No</B>.</LI>

<LI>
<TT>f</TT> as a member of <TT>A</TT> is private? <B>No</B>.</LI>

<LI>
<TT>f</TT> as a member of <TT>A</TT> is protected?
<B>Yes</B>.</LI>

<UL>
<LI>reference in a member or friend of <TT>A</TT>? <B>No</B>.</LI>

<LI>reference in a member or friend of a class derived from
<TT>A</TT>? <B>Yes</B>, <TT>B</TT>.</LI>

<UL>
<LI>
<TT>f</TT> as a member of <TT>B</TT> private or protected?
<B>No</B>, public.</LI>

</UL>
</UL>

<LI>base of <TT>A</TT> accessible at point of reference? <B>No</B>.</LI>
</UL>

<P>It seems clear to me that the third bullet should say "public,
private or protected".</P>

<P>
<U>Steve Adamczyk</U>:The words were written before
<I>using-declaration</I>s existed, and therefore didn't anticipate
this case.
</P>

<P>
<B>Proposed resolution (04/01):</B>
</P>

<P>Modify  the third bullet of the third change ("A member <I>m</I>
is accessible...") in the resolution
of <A HREF="
     cwg_defects.html#9">issue 9</A> to read "public, private,
or protected" instead of "private or protected."</P>

<BR>
<BR>
<HR>
<A NAME="77"></A>
<H4>77.
  
The definition of friend does not allow nested classes to be friends
</H4>
<B>Section: </B>11.4&nbsp;



 <A HREF="access.html#class.friend">class.friend</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Judy Ward
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>15 Dec 1998<BR>



<P>[Moved to DR at 4/02 meeting.]</P>

<P>The definition of "friend" in
11.4&nbsp;



 <A HREF="access.html#class.friend">class.friend</A>

says:</P>
<BLOCKQUOTE>A friend of a class is a function or class that is not a member
of the class but is permitted to use the private and protected member names
from the class. ...</BLOCKQUOTE>
A nested class, i.e. INNER in the example below, is a member of class OUTER.
The sentence above states that it cannot be a friend. I think this is a
mistake.
<PRE>
    class OUTER {
        class INNER;
        friend class INNER;
        class INNER {};
    };
</PRE>

<P>
<B>Proposed resolution (04/01):</B>
</P>

<P>Change the first sentence of 11.4&nbsp;



 <A HREF="access.html#class.friend">class.friend</A>
as follows:</P>

<BLOCKQUOTE>

A friend of a class is a function or class that is <S>not a
member of the class but is allowed</S> <B>given permission</B>
to use the private and protected member names from the class.
<S>The name of a friend is not in the scope of the class, and
the friend is not called with the member access operators
(5.2.5&nbsp;



 <A HREF="expr.html#expr.ref">expr.ref</A>) unless it is a member of
another class.</S> <B>A class specifies its friends, if any,
by way of friend declarations.  Such declarations give special
access rights to the friends, but they do not make the nominated
friends members of the befriending class.</B>

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="385"></A>
<H4>385.
  
How does protected member check of 11.5 interact with using-declarations?
</H4>
<B>Section: </B>11.5&nbsp;



 <A HREF="access.html#class.protected">class.protected</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Vincent Korstanje
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>24 Sep 2002<BR>


<P>[Voted into WP at October 2004 meeting.]</P>

<P>We consider it not unreasonable to do the following </P>
<PRE>
  class A { 
    protected: 
    void g();
  }; 
  class B : public A { 
    public: 
      using A::g; // B::g is a public synonym for A::g 
  }; 

  class C: public A {
    void foo();
  };

  void C::foo() { 
    B b; 
    b.g(); 
  } 
</PRE>
<P>However the EDG front-end does not like and gives the error</P>
<PRE>
  #410-D: protected function "A::g" is not accessible through a "B" pointer or  object 
    b.g();
      ^
</PRE>

<P>
<U>Steve Adamczyk</U>:
The error in this case is due to
11.5&nbsp;



 <A HREF="access.html#class.protected">class.protected</A> of the standard, which is an additional
check on top of the other access checking.  When that section says
"a protected nonstatic member function ... of a base class" it doesn't
indicate whether the fact that there is a using-declaration is relevant.
I'd say the current wording taken at face value would suggest that
the error is correct -- the function is protected, even if the
using-declaration for it makes it accessible as a public function.
But I'm quite sure the wording in
11.5&nbsp;



 <A HREF="access.html#class.protected">class.protected</A> was written before using-declarations
were invented and has not been reviewed since for consistency with
that addition.</P>

<P>
<B>Notes from April 2003 meeting:</B>
</P>

<P>We agreed that the example should be allowed.</P>

<P>
<B>Proposed resolution (April 2003, revised October 2003):</B>
</P>

<P>Change 11.5&nbsp;



 <A HREF="access.html#class.protected">class.protected</A> paragraph 1 from</P>

<BLOCKQUOTE>
When a friend or a member function of a derived class references a
protected nonstatic member function or protected nonstatic data member
of a base class, an access check applies in addition to those
described earlier in clause 11&nbsp;



 <A HREF="access.html#class.access">class.access</A>.
[Footnote: This
additional check does not apply to other members, <I>e.g. </I>static
data members or enumerator member constants.] Except
when forming a pointer to member (5.3.1&nbsp;



 <A HREF="expr.html#expr.unary.op">expr.unary.op</A>),
the access must be through a
pointer to, reference to, or object of the derived class itself (or
any class derived from that class (5.2.5&nbsp;



 <A HREF="expr.html#expr.ref">expr.ref</A>).
If the access is to form a
pointer to member, the <I>nested-name-specifier</I> shall name the
derived class (or any class derived from that class).
</BLOCKQUOTE>

<P>to</P>

<BLOCKQUOTE>
An additional access check beyond those described earlier in
clause 11&nbsp;



 <A HREF="access.html#class.access">class.access</A>
is applied when a nonstatic data member or nonstatic member
function is a protected member of its naming class
(11.2&nbsp;



 <A HREF="access.html#class.access.base">class.access.base</A>).
[Footnote: This additional check does not apply
to other members, e.g., static data members or enumerator member
constants.] As described 
earlier, access to a protected member is granted because the 
reference occurs in a friend or member of some
class <TT>C</TT>.  If the access is to form a pointer to member
(5.3.1&nbsp;



 <A HREF="expr.html#expr.unary.op">expr.unary.op</A>), the
<I>nested-name-specifier</I> shall name <TT>C</TT> or a
class derived from <TT>C</TT>.  All other accesses involve a
(possibly implicit) object expression (5.2.5&nbsp;



 <A HREF="expr.html#expr.ref">expr.ref</A>).
In this case, the
class of the object expression shall be <TT>C</TT> or a class derived
from <TT>C</TT>.
</BLOCKQUOTE>

<P>
<B>Additional discussion (September, 2004):</B>
</P>

<P>
<U>Steve Adamczyk:</U> I wonder if this wording is incorrect.  Consider:</P>

<PRE>
    class A {
    public:
      int p;
    };
    class B : protected A {
      // p is a protected member of B
    };
    class C : public B {
      friend void fr();
    };
    void fr() {
      B *pb = new B;
      pb-&gt;p = 1;  // Access okay?  Naming class is B, p is a protected member of B,
                  // the "C" of the issue 385 wording is C, but access is not via
                  // an object of type C or a derived class thereof.
    }
</PRE>

<P>I think the formulation that the member is a protected member
of its naming class is not what we want.  I think we intended
that the member is protected in the declaration that is found,
where the declaration found might be a <I>using-declaration</I>.
</P>

<P>
<U>Mike Miller:</U> I think the proposed wording makes the
access <TT>pb-&gt;p</TT> ill-formed, and I think that's the right
thing to do.</P>

<P>First, protected inheritance of <TT>A</TT> by <TT>B</TT> means
that <TT>B</TT> intends the public and protected members of
<TT>A</TT> to be part of <TT>B</TT>'s implementation, available
to <TT>B</TT>'s descendants only.  (That's why there's a
restriction on converting from <TT>B*</TT> to <TT>A*</TT>, to
enforce <TT>B</TT>'s intention on the use of members of
<TT>A</TT>.)  Consequently, I see no difference in access policy
between your example and</P>

<PRE>
    class B {
    protected:
        int p;
    };
</PRE>

<P>Second, the reason we have this rule is that <TT>C</TT>'s use
of inherited protected members might be different from their use
in a sibling class, say <TT>D</TT>.  Thus members and friends of
<TT>C</TT> can only use <TT>B::p</TT> in a manner consistent with
<TT>C</TT>'s usage, i.e., in <TT>C</TT> or
derived-from-<TT>C</TT> objects.  If we rewrote your example
slightly,</P>

<PRE>
    class D: public B { };

    void fr(B* pb) {
        pb-&gt;p = 1;
    }

    void g() {
        fr(new D);
    }
</PRE>

<P>it's clear that the intent of this rule is broken &mdash;
<TT>fr</TT> would be accessing <TT>B::p</TT> assuming
<TT>C</TT>'s policies when the object in question actually
required <TT>D</TT>'s policies.</P>

<P>(See also issues <A HREF="
     cwg_closed.html#471">471</A> and <A HREF="
     cwg_active.html#472">472</A>.)</P>

<BR>
<BR>
<HR>
<A NAME="10"></A>
<H4>10.
  
Can a nested class access its own class name as a qualified name if it is a private member of the enclosing class?
</H4>
<B>Section: </B>11.8&nbsp;



 <A HREF="access.html#class.access.nest">class.access.nest</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Josee Lajoie
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>unknown<BR>



<P>[Moved to DR at 4/01 meeting.]</P>



<P>Paragraph 1 says: "The members of a nested class have no special access
to members of an enclosing class..."</P>

<P>This prevents a member of a nested class from being defined outside
of its class definition. i.e. Should the following be well-formed?</P>
<PRE>
    class D {
        class E {
            static E* m;
        };
    };
     
    D::E* D::E::m = 1; // ill-formed
</PRE>
This is because the nested class does not have access to the member <TT>E</TT>
in <TT>D</TT>. 11&nbsp;



 <A HREF="access.html#class.access">class.access</A>

paragraph 5 says that access to <TT>D::E</TT> is checked with
member access to class <TT>E</TT>, but unfortunately that doesn't give
access to <TT>D::E</TT>. 11&nbsp;



 <A HREF="access.html#class.access">class.access</A>

paragraph 6 covers the access for <TT>D::E::m</TT>,
but it doesn't affect the <TT>D::E</TT> access. Are there any implementations
that are standard compliant that support this?

<P>Here is another example:</P>
<PRE>
    class C {
        class B
        {
            C::B *t; //2 error, C::B is inaccessible
        };
    };
</PRE>
This causes trouble for member functions declared outside of the class
member list. For example:
<PRE>
    class C {
        class B
        {
            B&amp; operator= (const B&amp;);
        };
    };
     
    C::B&amp; C::B::operator= (const B&amp;) { } //3
</PRE>
If the return type (i.e. <TT>C::B</TT>) is access checked in the scope
of class <TT>B</TT> (as implied by
11&nbsp;



 <A HREF="access.html#class.access">class.access</A>
 paragraph 5)
as a qualified name, then
the return type is an error just like referring to <TT>C::B</TT> in the
member list of class <TT>B</TT> above (i.e. //2) is ill-formed.

<P>
<B>Proposed resolution (04/01):</B>
</P>

<P>The resolution for this issue is incorporated into the
resolution for <A HREF="
     cwg_defects.html#45">issue 45</A>.</P>
<BR>
<BR>
<HR>
<A NAME="45"></A>
<H4>45.
  
Access to nested classes
</H4>
<B>Section: </B>11.8&nbsp;



 <A HREF="access.html#class.access.nest">class.access.nest</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Daveed Vandevoorde
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>29 Sep 1998<BR>



<P>[Moved to DR at 4/01 meeting.]</P>



<P>Example:</P>
<PRE>
    #include &lt;iostream.h&gt;
    
    class C {  // entire body is private
        struct Parent {
            Parent() { cout &lt;&lt; "C::Parent::Parent()\n"; }
        };
    
        struct Derived : Parent {
            Derived() { cout &lt;&lt; "C::Derived::Derived()\n"; }
        };
    
        Derived d;
    };
    
    
    int main() {
        C c;      //  Prints message from both nested classes
        return 0;
    }
</PRE>
How legal/illegal is this? Paragraphs that seem to apply here are:
<P>11&nbsp;



 <A HREF="access.html#class.access">class.access</A>
 paragraph 1:</P>
<BLOCKQUOTE>
A member of a class can be
<UL>
<LI>
<TT>private</TT>; that is, its name can be used only by members and
friends of the class in which it is declared. [...]</LI>
</UL>
</BLOCKQUOTE>
and
11.8&nbsp;



 <A HREF="access.html#class.access.nest">class.access.nest</A>

paragraph 1:
<BLOCKQUOTE>
The members of a nested class
have no special access to members of an enclosing class, nor to classes
or functions that have granted friendship to an enclosing class; the usual
access rules (clause 11&nbsp;



 <A HREF="access.html#class.access">class.access</A>
)
shall be obeyed. [...]</BLOCKQUOTE>
This makes me think that the '<TT>: Parent</TT>' part is OK by itself,
but that the implicit call of '<TT>Parent::Parent()</TT>' by '<TT>Derived::Derived()</TT>'
is not.

<P>
<U>From Mike Miller:</U>
</P>

<P>I think it is completely legal, by the reasoning given in the (non-normative)
11.8&nbsp;



 <A HREF="access.html#class.access.nest">class.access.nest</A>

paragraph 2. The use of a private nested class as a base of another nested class
is explicitly declared to be acceptable there. I think the rationale in
the comments in the example ("// OK because of injection of name A in A")
presupposes that public members of the base class will be public members
in a (publicly-derived) derived class, regardless of the access of the
base class, so the constructor invocation should be okay as well.</P>

<P>I can't find anything normative that explicitly says that,
though.</P>

<P>(See also papers J16/99-0009 = WG21 N1186,
J16/00-0031 = WG21 N1254, and J16/00-0045 = WG21 N1268.)</P>

<P>
<B>Proposed Resolution (04/01):</B>
</P>

<OL>

<LI>
<P>Insert the following as a new paragraph following
11&nbsp;



 <A HREF="access.html#class.access">class.access</A> paragraph 1:</P>

<BLOCKQUOTE>

A member of a class can also access all names as the class of which
it is a member.  A local class of a member function may access the
same names that the member function itself may access.  [<I>Footnote:</I>
Access permissions are thus transitive and cumulative to nested and
local classes.]

</BLOCKQUOTE>
</LI>

<LI>
<P>Delete 11&nbsp;



 <A HREF="access.html#class.access">class.access</A> paragraph 6.</P>
</LI>

<LI>
<P>In 11.8&nbsp;



 <A HREF="access.html#class.access.nest">class.access.nest</A> paragraph 1, change</P>

<BLOCKQUOTE>

The members of a nested class have no special access to members of an
enclosing class, nor to classes or functions that have granted
friendship to an enclosing class; the usual access rules
(clause 11&nbsp;



 <A HREF="access.html#class.access">class.access</A>) shall be obeyed.

</BLOCKQUOTE>

<P>to</P>

<BLOCKQUOTE>

A nested class is a member and as such has the same access rights
as any other member.

</BLOCKQUOTE>

<P>Change</P>

<PRE>
    B b;       // error: E::B is private
</PRE>

<P>to</P>

<PRE>
    B b;       // Okay, E::I can access E::B
</PRE>

<P>Change</P>

<PRE>
    p-&gt;x = i;      // error: E::x is private
</PRE>

<P>to</P>

<PRE>
    p-&gt;x = i;      // Okay, E::I can access E::x
</PRE>

</LI>

<LI>
<P>Delete 11.8&nbsp;



 <A HREF="access.html#class.access.nest">class.access.nest</A> paragraph 2.</P>
</LI>

</OL>

<P>(This resolution also resolves issues
<A HREF="
     cwg_defects.html#8">8</A> and
<A HREF="
     cwg_defects.html#10">10</A>.</P>

<BR>
<BR>
<HR>
<A NAME="263"></A>
<H4>263.
  
Can a constructor be declared a friend?
</H4>
<B>Section: </B>12.1&nbsp;



 <A HREF="special.html#class.ctor">class.ctor</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Martin Sebor
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>13 Nov 2000<BR>


<P>[Voted into WP at April 2003 meeting.]</P>



<P>According to 12.1&nbsp;



 <A HREF="special.html#class.ctor">class.ctor</A> paragraph 1, a
declaration of a constructor has a special limited syntax, in
which only <I>function-specifier</I>s are allowed.  A <TT>friend</TT>
specifier is not a <I>function-specifier</I>, so one interpretation
is that a constructor cannot be declared in a <TT>friend</TT>
declaration.</P>

<P>(It should also be noted, however, that neither <TT>friend</TT>
nor <I>function-specifier</I> is part of the <B>declarator</B>
syntax, so it's not clear that anything conclusive can be derived
from the wording of 12.1&nbsp;



 <A HREF="special.html#class.ctor">class.ctor</A>.)</P>

<P>
<B>Notes from 04/01 meeting:</B>
</P>

<P>The consensus of the core language working group was that it
should be permitted to declare constructors as <TT>friend</TT>s.</P>

<P>
<B>Proposed Resolution (revised October 2002):</B>
</P>

<P>Change paragraph 1a in 3.4.3.1&nbsp;



 <A HREF="basic.html#class.qual">class.qual</A> (added by
the resolution of issue 147) as follows:</P>
<BLOCKQUOTE>
If the <I>nested-name-specifier</I> nominates a class <TT>C</TT>, and the
name specified after the <I>nested-name-specifier</I>, when looked up in
<TT>C</TT>, is the injected-class-name of <TT>C</TT> (clause
9&nbsp;



 <A HREF="class.html#class">class</A>), the name is instead considered to name the
constructor of class <TT>C</TT>. Such a constructor name shall be used
only in the <I>declarator-id</I> of a <S>constructor definition</S>
<B>declaration</B> that <S>appears outside of the class definition</S>
<B>names a constructor</B>.... 
</BLOCKQUOTE>

<P>Note: the above does not allow qualified names to be used for
in-class declarations; see 8.3&nbsp;



 <A HREF="decl.html#dcl.meaning">dcl.meaning</A> paragraph 1.
Also note that <A HREF="
     cwg_defects.html#318">issue 318</A> updates the
same paragraph.</P>

<P>Change the example in 11.4&nbsp;



 <A HREF="access.html#class.friend">class.friend</A>, paragraph 4
as follows:</P>
<PRE>
class Y {
  friend char* X::foo(int);
  <B>friend X::X(char);   // constructors can be friends</B>
  <B>friend X::~X();      // destructors can be friends</B>
  //...
};
</PRE>

<BR>
<BR>
<HR>
<A NAME="326"></A>
<H4>326.
  
Wording for definition of trivial constructor
</H4>
<B>Section: </B>12.1&nbsp;



 <A HREF="special.html#class.ctor">class.ctor</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>James Kanze
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>9 Dec 2001<BR>


<P>[Voted into WP at October 2003 meeting.]</P>



<P>In 12.1&nbsp;



 <A HREF="special.html#class.ctor">class.ctor</A> paragraph 5, the standard says
"A constructor is trivial if [...]", and goes on to define a trivial
default constructor.  Taken literally, this would mean that a copy
constructor can't be trivial (contrary to 12.8&nbsp;



 <A HREF="special.html#class.copy">class.copy</A> paragraph 6).  I suggest changing this to "A default
constructor is trivial if [...]".  (I think the change is purely
editorial.)</P>

<P>
<B>Proposed Resolution (revised October 2002):</B>
</P>

<P>Change 12.1&nbsp;



 <A HREF="special.html#class.ctor">class.ctor</A> paragraph 5-6 as follows: </P>
<BLOCKQUOTE>
<P>
A <I>default</I> constructor for a class <TT>X</TT>
is a constructor of class <TT>X</TT>
that can be called without an argument.
If there is no
<S><I>user-declared</I></S>
<B>user-declared</B>
constructor for class <TT>X</TT>,
a default constructor is implicitly declared.
An
<S><I>implicitly-declared</I></S>
<B>implicitly-declared</B>
default constructor
is an <TT>inline public</TT> member of its class.
A
<B>default</B>
constructor is <I>trivial</I>
if it is <S>an</S> implicitly-declared <S>default constructor</S>
and if:
<UL>
<LI>
its class has no virtual functions (10.3&nbsp;



 <A HREF="derived.html#class.virtual">class.virtual</A>)
and no virtual base classes (10.1&nbsp;



 <A HREF="derived.html#class.mi">class.mi</A>), and
</LI>
<LI>
all the direct base classes of its class
have trivial
<B>default</B>
constructors, and
</LI>
<LI>
for all the nonstatic data members of its class
that are of class type (or array thereof),
each such class has a trivial
<B>default</B>
constructor.
</LI>
</UL>
</P>
<P>
Otherwise, the
<B>default</B>
constructor is non-trivial.
</P>
</BLOCKQUOTE>
<P>
Change 12.4&nbsp;



 <A HREF="special.html#class.dtor">class.dtor</A> paragraphs 3-4 as follows (the main
changes are removing italics):</P>
<BLOCKQUOTE>
<P>If a class has no
<S><I>user-declared</I></S>
<B>user-declared</B>
destructor, a destructor  is  declared
implicitly.   An
<S><I>implicitly-declared</I></S>
<B>implicitly-declared</B>
destructor  is an <TT>inline public</TT>
member of its class.  A destructor is <I>trivial</I> if it is <S>an</S>
implicitly-declared <S>destructor</S> and if:
<UL>
<LI>
all of the direct base classes of its class have trivial destructors and
</LI>
<LI>
for all of the non-static data members of  its  class  that  are  of
class  type  (or  array  thereof),  each  such  class  has a trivial
destructor.
</LI>
</UL>
</P>
<P>Otherwise, the destructor is
<S><I>non-trivial</I></S>
<B>non-trivial</B>.
</P>
</BLOCKQUOTE>

<P>
In 9.5&nbsp;



 <A HREF="class.html#class.union">class.union</A> paragraph 1, change "trivial constructor"
to "trivial default constructor".
</P>

<P>
In 12.2&nbsp;



 <A HREF="special.html#class.temporary">class.temporary</A> paragraph 3, add to the reference to
12.1&nbsp;



 <A HREF="special.html#class.ctor">class.ctor</A> a second reference, to
12.8&nbsp;



 <A HREF="special.html#class.copy">class.copy</A>.</P>

<BR>
<BR>
<HR>
<A NAME="331"></A>
<H4>331.
  
Allowed copy constructor signatures
</H4>
<B>Section: </B>12.1&nbsp;



 <A HREF="special.html#class.ctor">class.ctor</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Richard Smith
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>8 Jan 2002<BR>


<P>[Voted into WP at October 2003 meeting.]</P>

<P>12.1&nbsp;



 <A HREF="special.html#class.ctor">class.ctor</A> paragraph 10 states</P>
<BLOCKQUOTE>
A copy constructor for a class X is a constructor with a
first parameter of type X &amp; or of type const X &amp;.  [Note:
see 12.8&nbsp;



 <A HREF="special.html#class.copy">class.copy</A> for more information on copy constructors.]
</BLOCKQUOTE>

<P>No mention is made of constructors with first parameters of types
volatile X &amp; or const volatile X &amp;.  This statement seems to be
in contradiction with 12.8&nbsp;



 <A HREF="special.html#class.copy">class.copy</A> paragraph 2 which states</P>
<BLOCKQUOTE>
A non-template constructor for class X is a copy constructor
if its first parameter is of type X &amp;, const X &amp;, volatile X &amp;
or const volatile X &amp;, ...
</BLOCKQUOTE>

<P>12.8&nbsp;



 <A HREF="special.html#class.copy">class.copy</A> paragraph 5 also mentions the volatile
versions of the
copy constructor, and the comparable paragraphs for copy assignment
(12.8&nbsp;



 <A HREF="special.html#class.copy">class.copy</A> paragraphs 9 and 10) all allow volatile
versions, so it seems that 12.1&nbsp;



 <A HREF="special.html#class.ctor">class.ctor</A> is at fault.</P>

<P>
<B>Proposed resolution (October 2002):</B>
</P>

<P>Change 12.1&nbsp;



 <A HREF="special.html#class.ctor">class.ctor</A> paragraph 10 from
<BLOCKQUOTE>
A <I>copy constructor</I> for a class <TT>X</TT> is a constructor with a
first parameter of type <TT>X&amp;</TT> or of type <TT>const X&amp;</TT>.
[<I>Note:</I> see 12.8&nbsp;



 <A HREF="special.html#class.copy">class.copy</A> for more information on
copy constructors. ]
</BLOCKQUOTE>
to (note that the dropping of italics is intentional):
<BLOCKQUOTE>
A copy constructor (12.8&nbsp;



 <A HREF="special.html#class.copy">class.copy</A>) is used to copy objects
of class type. 
</BLOCKQUOTE>
</P>

<BR>
<BR>
<HR>
<A NAME="86"></A>
<H4>86.
  
Lifetime of temporaries in query expressions
</H4>
<B>Section: </B>12.2&nbsp;



 <A HREF="special.html#class.temporary">class.temporary</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Adamczyk
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>Jan 1999<BR>



<P>[Voted into WP at April, 2006 meeting.]</P>

<P>In
12.2&nbsp;



 <A HREF="special.html#class.temporary">class.temporary</A>

 paragraph 5,
should binding a reference to the result of a "<TT>?</TT>" operation, each
of whose branches is a temporary, extend both temporaries?</P>

<P>Here's an example:</P>
<PRE>
    const SFileName &amp;C = noDir ? SFileName("abc") : SFileName("bcd");
</PRE>
<P>Do the temporaries created by the <TT>SFileName</TT> conversions survive
the end of the full expression?</P>

<P>
<B>Notes from 10/00 meeting:</B>
</P>

<P>Other problematic examples include cases where the temporary
from one branch is a base class of the temporary from the other (i.e.,
where the implementation must remember which type of temporary must
be destroyed), or where one branch is a temporary and the other is
not.  Similar questions also apply to the comma operator.  The sense
of the core language working group was that implementations should
be required to support these kinds of code.</P>

<P>
<B>Notes from the March 2004 meeting:</B>
</P>

<P>We decided that the cleanest model is one in which any "?" operation
that returns a class rvalue always copies one of its operands to
a temporary and returns the temporary as the result of the operation.
(Note that this may involve slicing.)  An implementation would be
free to optimize this using the rules in 12.8&nbsp;



 <A HREF="special.html#class.copy">class.copy</A>
paragraph 15, and in fact we would expect that in many cases
compilers would do such optimizations.  For example, the compiler
could construct both rvalues in the above example into a
single temporary, and thus avoid a copy.</P>

<P>See also <A HREF="
     cwg_defects.html#446">issue 446</A>.</P>

<P>
<B>Proposed resolution (October, 2004):</B>
</P>

<P>This issue is resolved by the resolutions of <A HREF="
     cwg_defects.html#446">issue 446</A>.</P>

<P>
<B>Note (October, 2005):</B>
</P>

<P>This issue was overlooked when <A HREF="
     cwg_defects.html#446">issue 446</A>
was moved to &ldquo;ready&rdquo; status and was thus inadvertently
omitted from the list of issues accepted as Defect Reports at the
October, 2005 meeting.</P>

<BR>
<BR>
<HR>
<A NAME="124"></A>
<H4>124.
  
Lifetime of temporaries in default initialization of class arrays
</H4>
<B>Section: </B>12.2&nbsp;



 <A HREF="special.html#class.temporary">class.temporary</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Jack Rouse
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>3 June 1999<BR>



<P>[Moved to DR at 4/01 meeting.]</P>



<P>
<U>Jack Rouse:</U>
12.2&nbsp;



 <A HREF="special.html#class.temporary">class.temporary</A>

states that temporary objects will normally be destroyed at the
end of the full expression in which they are created.  This can create
some unique code generation requirements when initializing a class
array with a default constructor that uses a default argument.  Consider
the code:</P>

<PRE>
    struct T {
       int i;
       T( int );
       ~T();
    };

    struct S {
       S( int = T(0).i );
       ~S();
    };

    S* f( int n )
    {
       return new S[n];
    }
</PRE>

The full expression allocating the array in <TT>f(int)</TT> includes the
default constructor for <TT>S</TT>.  Therefore according to
1.9&nbsp;



 <A HREF="intro.html#intro.execution">intro.execution</A> paragraph 14, it
includes the default argument expression for <TT>S(int)</TT>.
So evaluation of
the full expression should include evaluating the default argument "n"
times and creating "n" temporaries of type <TT>T</TT>.  But the destruction of
the temporaries must be delayed until the end of the full expression
so this requires allocating space at runtime for "n" distinct
temporaries.  It is unclear how these temporaries are supposed to be
allocated and deallocated.  They cannot readily be autos because a
variable allocation is required.

<P>I believe that many existing implementations will destroy the
temporaries needed by the default constructor after each array element
is initialized.  But I can't find anything in the standard that allows
the temporaries to be destroyed early in this case.</P>

<P>I think the standard should allow the early destruction of temporaries
used in the default initialization of class array elements.  I believe
early destruction is the status quo, and I don't think the users of
existing C++ compilers have been adversely impacted by it.</P>

<P>
<B>Proposed resolution (04/01):</B>
</P>

<P>The proposed resolution is contained in the proposal for
<A HREF="
     cwg_defects.html#201">issue 201</A>.</P>
<BR>
<BR>
<HR>
<A NAME="201"></A>
<H4>201.
  
Order of destruction of temporaries in initializers
</H4>
<B>Section: </B>12.2&nbsp;



 <A HREF="special.html#class.temporary">class.temporary</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Alan Nash
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>31 Jan 2000<BR>



<P>[Moved to DR at 4/01 meeting.]</P>



<P>According to 12.2&nbsp;



 <A HREF="special.html#class.temporary">class.temporary</A>

paragraph 4, an expression appearing as the initializer in an object
definition constitutes a context "in which temporaries are destroyed
at a different point than the end of the full-expression."  It goes on
to say that the temporary containing the value of the expression
persists until after the initialization is complete (see also
<A HREF="
     cwg_closed.html#117">issue 117</A>).  This seems to presume
that the end of the full-expression is a point earlier than the
completion of the initialization.</P>

<P>However, according to
1.9&nbsp;



 <A HREF="intro.html#intro.execution">intro.execution</A>
 paragraphs 12-13, the
full-expression in such cases is, in fact, the entire initialization.
If this is the case, the behavior described for temporaries in an
initializer expression is simply the normal behavior of temporaries in
any expression, and treating it as an exception to the general rule is
both incorrect and confusing.</P>

<P>
<B>Proposed resolution (04/01):</B>
</P>

<P>
<I>[Note: this proposal also addresses <A HREF="
     cwg_defects.html#124">issue 124</A>.]</I>
</P>

<OL>

<LI>
<P>Add to the end of 1.9&nbsp;



 <A HREF="intro.html#intro.execution">intro.execution</A> paragraph 12:</P>

<BLOCKQUOTE>

If the initializer for an object or
sub-object is a full-expression, the initialization of
the object or sub-object (e.g., by calling a constructor
or copying an expression value) is considered to be part
of the full-expression.

</BLOCKQUOTE>
</LI>

<LI>
<P>Replace 12.2&nbsp;



 <A HREF="special.html#class.temporary">class.temporary</A> paragraph 4 with:</P>

<BLOCKQUOTE>

There are two contexts in which temporaries are
destroyed at a different point than the end of the
full-expression.  The first context is when a
default constructor is called to initialize an
element of an array.  If the constructor has one
or more default arguments, any temporaries created
in the default argument expressions are destroyed
immediately after return from the constructor.

</BLOCKQUOTE>
</LI>

</OL>

<BR>
<BR>
<HR>
<A NAME="320"></A>
<H4>320.
  
Question on copy constructor elision example
</H4>
<B>Section: </B>12.2&nbsp;



 <A HREF="special.html#class.temporary">class.temporary</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Clamage
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>2 Nov 2001<BR>


<P>[Voted into WP at April 2005 meeting.]</P>

<P>Section 12.2&nbsp;



 <A HREF="special.html#class.temporary">class.temporary</A> paragraph 2, abridged:</P>
<BLOCKQUOTE>
<PRE>
  X f(X);
  void g()
  {
	X a;
	a = f(a);
  }
</PRE>
<P>
<TT>a=f(a)</TT> requires a temporary for either the argument <TT>a</TT>
or the result of <TT>f(a)</TT> to avoid undesired aliasing of <TT>a</TT>.
</P>
</BLOCKQUOTE>

<P>The note seems to imply that an implementation is allowed to omit
copying "a" to f's formal argument, or to omit using a temporary for
the return value of f.  I don't find that license in normative text.</P>

<P>Function f returns an X by value, and in the expression the value is
assigned (not copy-constructed) to "a".  I don't see how that
temporary can be omitted.  (See also 12.8&nbsp;



 <A HREF="special.html#class.copy">class.copy</A> p 15)</P>

<P>Since "a" is an lvalue and not a temporary, I don't see how copying
"a" to f's formal parameter can be avoided.</P>

<P>Am I missing something, or is 12.2&nbsp;



 <A HREF="special.html#class.temporary">class.temporary</A> p 2
misleading?</P>

<P>
<B>Proposed resolution (October, 2004):</B>
</P>

<P>In 12.2&nbsp;



 <A HREF="special.html#class.temporary">class.temporary</A> paragraph 2, change the last
sentence as indicated:</P>

<BLOCKQUOTE>

On the other hand, the expression <TT>a=f(a)</TT> requires a
temporary for <S>either the argument <TT>a</TT> or the result of
<TT>f(a)</TT> to avoid undesired aliasing of <TT>a</TT></S>
<B>the result of <TT>f(a)</TT>, which is then assigned to
<TT>a</TT></B>.

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="392"></A>
<H4>392.
  
Use of full expression lvalue before temporary destruction
</H4>
<B>Section: </B>12.2&nbsp;



 <A HREF="special.html#class.temporary">class.temporary</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Stephen Clamage
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>21 Nov 2002<BR>


<P>[Voted into WP at March 2004 meeting.]</P>



<PRE>
class C {
public:
    C();
    ~C();
    int&amp; get() { return p; } // reference return
private:
    int p;
};

int main ()
{
    if ( C().get() ) // OK?
}
</PRE>

<P>Section 12.2&nbsp;



 <A HREF="special.html#class.temporary">class.temporary</A> paragraph 3 says a temp is
destroyed as the last step in
evaluating the full expression.  But the expression C().get() has a
reference type.  Does 12.2&nbsp;



 <A HREF="special.html#class.temporary">class.temporary</A> paragraph 3 require
that the dereference to get a
boolean result occur before the destructor runs, making the code
valid?  Or does the code have undefined behavior?</P>

<P>
<U>Bill Gibbons:</U>
It has undefined behavior, though clearly this wasn't intended.
The lvalue-to-rvalue conversion that occurs in the "if" statement is
not currently part of the full-expression.</P>

<P>From section 12.2&nbsp;



 <A HREF="special.html#class.temporary">class.temporary</A> paragraph 3:</P>
<BLOCKQUOTE>
   Temporary objects are destroyed as the last step in evaluating
   the full-expression (1.9&nbsp;



 <A HREF="intro.html#intro.execution">intro.execution</A>)
that (lexically) contains the point
   where they were created.
</BLOCKQUOTE>

<P>From section 1.9&nbsp;



 <A HREF="intro.html#intro.execution">intro.execution</A> paragraph 12:</P>
<BLOCKQUOTE>
   A full-expression is an expression that is not a subexpression
   of another expression. If a language construct is defined to
   produce an implicit call of a function, a use of the language
   construct is considered to be an expression for the purposes
   of this definition.
</BLOCKQUOTE>

<P>The note in section 1.9&nbsp;



 <A HREF="intro.html#intro.execution">intro.execution</A> paragraph 12 goes
on to explain that this covers
expressions used as initializers, but it does not discuss
lvalues within temporaries.</P>

<P>It is a small point but it is probably worth correcting
1.9&nbsp;



 <A HREF="intro.html#intro.execution">intro.execution</A> paragraph 12.
Instead of the "implicit call of a function" wording, it might
be better to just say that a full-expression includes any implicit
use of the expression value in the enclosing language construct,
and include a note giving implicit calls and lvalue-to-rvalue
conversions as examples.</P>

<P>Offhand the places where this matters include:

   initialization (including member initializers),
   selection statements,
   iteration statements,
   return,
   throw
</P>

<P>
<B>Proposed resolution (April 2003):</B>
</P>

<P>Change 1.9&nbsp;



 <A HREF="intro.html#intro.execution">intro.execution</A> paragraph 12-13 to read:</P>
<BLOCKQUOTE>
<P>A <I>full-expression</I> is an expression that is not a
subexpression of another expression.  If a language construct is
defined to produce an implicit call of a function, a use of the
language construct is considered to be an expression for the
purposes of this definition.  <B>Conversions applied to the result of
an expression in order to satisfy the requirements of the language
construct in which the expression appears are also considered to be
part of the full-expression.
</B>
</P>

<S>
<P>[<I>Note:</I> certain contexts in C++ cause the evaluation
of a full-expression that results from a syntactic construct other
than <I>expression</I> (5.18&nbsp;



 <A HREF="expr.html#expr.comma">expr.comma</A>).  For example,
in 8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A> one syntax for
<I>initializer</I> is</P>

<UL>
<P>
<TT>( </TT><I>expression-list</I><TT> )</TT>
</P>
</UL>

<P>but the resulting construct is a function call upon a constructor
function with <I>expression-list</I> as an argument list; such a
function call is a full-expression.  For example, in
8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A>, another
syntax for <I>initializer</I> is</P>

<UL>
<P>
<TT>= </TT><I>initializer-clause</I>
</P>
</UL>
</S>

<P>
<S>but again the resulting construct might be a function call upon a
constructor function with one <I>assignment-expression</I> as an
argument; again, the function call is a full-expression. ]</S>
<B>[<I>Example:</I></B>
</P>
<B>
<PRE>
  struct S {
      S(int i): I(i) { }
      int&amp; v() { return I; }
    private:
      int I;
  };

  S s1(1);           // <I>full-expression is call of S::S(int)</I>
  S s2 = 2;          // <I>full-expression is call of S::S(int)</I>

  void f() {
      if (S(3).v())  // <I>full-expression includes lvalue-to-rvalue and</I>
                     // int<I> to</I> bool<I> conversions, performed before</I>
                     // <I>temporary is deleted at end of full-expression</I>
      { }
  }
</PRE>

<P>--- <I>end example</I>]</P>
</B>
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="443"></A>
<H4>443.
  
Wording nit in description of lifetime of temporaries
</H4>
<B>Section: </B>12.2&nbsp;



 <A HREF="special.html#class.temporary">class.temporary</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Matthias Hofmann
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>2 Dec 2003<BR>


<P>[Voted into WP at April 2005 meeting.]</P>

<P>There seems to be a typo in
12.2&nbsp;



 <A HREF="special.html#class.temporary">class.temporary</A>/5, which says "The temporary to which
the reference is bound or the temporary that is the complete object TO a
subobject OF which the TEMPORARY is bound persists for the lifetime of the
reference except as specified below."</P>

<P>I think this should be "The temporary to which the reference is bound or the
temporary that is the complete object OF a subobject TO which the REFERENCE
is bound persists for the lifetime of the reference except as specified
below."</P>

<P>I used upper-case letters for the parts I think need to be
changed.</P>

<P>
<B>Proposed resolution (October, 2004):</B>
</P>

<P>Change 12.2&nbsp;



 <A HREF="special.html#class.temporary">class.temporary</A> paragraph 5 as
indicated:</P>

<BLOCKQUOTE>

The temporary to which the reference is bound or the temporary
that is the complete object <S>to</S> <B>of</B> a subobject
<S>of</S> <B>to</B> which the <S>temporary</S> <B>reference</B>
is bound persists for the lifetime of the reference except as
specified below.

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="464"></A>
<H4>464.
  
Wording nit on lifetime of temporaries to which references are bound
</H4>
<B>Section: </B>12.2&nbsp;



 <A HREF="special.html#class.temporary">class.temporary</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Allan Odgaard
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>21 Feb 2004<BR>


<P>[Voted into WP at April, 2006 meeting.]</P>

<P>Section 12.2&nbsp;



 <A HREF="special.html#class.temporary">class.temporary</A> paragraph 5 ends with this "rule":</P>
<BLOCKSCOPE>
    [...] if obj2 is an object with static or automatic
    storage  duration created  after  the temporary  is
    created,  the temporary  shall  be destroyed  after
    obj2 is destroyed.
</BLOCKSCOPE>
<P>For the temporary to be destroyed after obj2 is destroyed, when obj2 has
static storage, I would say that the reference to the temporary should
also have static storage, but that is IMHO not clear from the
paragraph.</P>

<P>Example:</P>
<PRE>
    void f ()
    {
       const T1&amp; ref = T1();
       static T2 obj2;
       ...
    }
</PRE>
<P>Here the temporary would be destoyed <I>before</I> obj2, contrary to the
rule above.</P>

<P>
<U>Steve Adamczyk:</U> I agree there's a minor issue here.  I think
the clause quoted above meant for obj1 and obj2 to have the same storage
duration.  Replacing "obj2 is an object with static or automatic
storage duration" by "obj2 is an object with the same storage duration as
obj1" would, I believe, fix the problem.</P>

<P>
<B>Notes from October 2004 meeting:</B>
</P>

<P>We agreed with Steve Adamczyk's suggestion.</P>

<P>
<B>Proposed resolution (October, 2005):</B>
</P>

<P>Change 12.2&nbsp;



 <A HREF="special.html#class.temporary">class.temporary</A> paragraph 5 as follows:</P>

<BLOCKQUOTE>

... In addition, the destruction of temporaries bound to references
shall take into account the ordering of destruction of objects with
static or automatic storage duration (3.7.1&nbsp;



 <A HREF="basic.html#basic.stc.static">basic.stc.static</A>,
3.7.2&nbsp;



 <A HREF="basic.html#basic.stc.auto">basic.stc.auto</A>); that is, if <TT>obj1</TT> is an object
<S>with static or automatic storage duration</S> created before the
temporary is created <B>with the same storage duration as the
temporary</B>, the temporary shall be destroyed before <TT>obj1</TT>
is destroyed; if <TT>obj2</TT> is an object <S>with static or
automatic storage duration</S> created after the temporary is
created <B>with the same storage duration as the temporary</B>, the
temporary shall be destroyed after <TT>obj2</TT> is destroyed...

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="296"></A>
<H4>296.
  
Can conversion functions be static?
</H4>
<B>Section: </B>12.3.2&nbsp;



 <A HREF="special.html#class.conv.fct">class.conv.fct</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Scott Meyers
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>5 Jul 2001<BR>


<P>[Moved to DR at October 2002 meeting.]</P>

<P>May user-defined conversion functions be static?  That is, should this
compile?</P>
<PRE>
    class Widget {
    public:
      static operator bool() { return true; }
    };
</PRE>
<P>All my compilers hate it.  I hate it, too.  However, I don't see anything
in 12.3.2&nbsp;



 <A HREF="special.html#class.conv.fct">class.conv.fct</A> that makes it illegal.  Is this a
prohibition that arises from
the grammar, i.e., the grammar doesn't allow "static" to be followed by a
<I>conversion-function-id</I> in a member function declaration?  Or am I just
overlooking something obvious that forbids static conversion functions?</P>

<P>
<B>Proposed Resolution (4/02):</B>
</P>

<P>Add to 12.3.2&nbsp;



 <A HREF="special.html#class.conv.fct">class.conv.fct</A> as a new paragraph 7:</P>

<BLOCKQUOTE>
Conversion functions cannot be declared <TT>static</TT>.
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="244"></A>
<H4>244.
  
Destructor lookup
</H4>
<B>Section: </B>12.4&nbsp;



 <A HREF="special.html#class.dtor">class.dtor</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>John Spicer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>6 Sep 2000<BR>


<P>[Moved to DR at October 2002 meeting.]</P>



<P>12.4&nbsp;



 <A HREF="special.html#class.dtor">class.dtor</A> contains this example:</P>

<PRE>
    struct B {
        virtual ~B() { }
    };
    struct D : B {
        ~D() { }
    };

    D D_object;
    typedef B B_alias;
    B* B_ptr = &amp;D_object;

    void f() {
        D_object.B::~B();               // calls B's destructor
        B_ptr-&gt;~B();                    // calls D's destructor
        B_ptr-&gt;~B_alias();              // calls D's destructor
        B_ptr-&gt;B_alias::~B();           // calls B's destructor
        B_ptr-&gt;B_alias::~B_alias();     // error, no B_alias in class B
    }
</PRE>

<P>On the other hand, 3.4.3&nbsp;



 <A HREF="basic.html#basic.lookup.qual">basic.lookup.qual</A> contains this
example:</P>

<PRE>
    struct C {
        typedef int I;
    };
    typedef int I1, I2;
    extern int* p;
    extern int* q;
    p-&gt;C::I::~I();       // I is looked up in the scope of C
    q-&gt;I1::~I2();        // I2 is looked up in the scope of
                         // the postfix-expression
    struct A {
        ~A();
    };
    typedef A AB;
    int main()
    {
        AB *p;
        p-&gt;AB::~AB();    // explicitly calls the destructor for A
    }
</PRE>

<P>Note that</P>

<PRE>
     B_ptr-&gt;B_alias::~B_alias();
</PRE>

<P>is claimed to be an error, while the equivalent</P>

<PRE>
     p-&gt;AB::~AB();
</PRE>

<P>is claimed to be well-formed.</P>

<P>I believe that clause 3 is correct and that clause 12 is in error.
We worked hard to get the destructor lookup rules in clause 3 to be
right, and I think we failed to notice that a change was also needed
in clause 12.</P>

<P>
<U>Mike Miller</U>:</P>

<P>Unfortunately, I don't believe 3.4.3&nbsp;



 <A HREF="basic.html#basic.lookup.qual">basic.lookup.qual</A> covers
the case of <TT>p-&gt;AB::~AB()</TT>.  It's clearly intended to do so, as
evidenced by 3.4.3.1&nbsp;



 <A HREF="basic.html#class.qual">class.qual</A> paragraph 1 ("a
destructor name is looked up as specified in 3.4.3&nbsp;



 <A HREF="basic.html#basic.lookup.qual">basic.lookup.qual</A>"), but I don't think the language there does so.</P>

<P>The relevant paragraph is 3.4.3&nbsp;



 <A HREF="basic.html#basic.lookup.qual">basic.lookup.qual</A> paragraph
5.  (None of the other paragraphs in that section deal with this topic
at all.)  It has two parts.  The first is</P>

<BLOCKQUOTE>
If a <I>pseudo-destructor-name</I> (5.2.4&nbsp;



 <A HREF="expr.html#expr.pseudo">expr.pseudo</A>)
contains a <I>nested-name-specifier</I>, the <I>type-name</I>s are
looked up as types in the scope designated by the
<I>nested-name-specifier</I>.
</BLOCKQUOTE>

<P>This sentence doesn't apply, because <TT>~AB</TT> isn't a
<I>pseudo-destructor-name</I>.  5.2.4&nbsp;



 <A HREF="expr.html#expr.pseudo">expr.pseudo</A> makes
clear that this syntactic production (5.2&nbsp;



 <A HREF="expr.html#expr.post">expr.post</A>
paragraph 1) only applies to cases where the <I>type-name</I> is not a
<I>class-name</I>.  <TT>p-&gt;AB::~AB</TT> is covered by the production
using <I>id-expression</I>.</P>

<P>The second part of 3.4.3&nbsp;



 <A HREF="basic.html#basic.lookup.qual">basic.lookup.qual</A> paragraph 5 says</P>

<BLOCKQUOTE>
<P>In a <I>qualified-id</I> of the form:</P>

<OL>
<TT>::</TT><SUB>opt</SUB>&nbsp;<I>nested-name-specifier</I>&nbsp;<TT>~</TT>&nbsp;<I>class-name</I>
</OL>

<P>where the <I>nested-name-specifier</I> designates a namespace name,
and in a <I>qualified-id</I> of the form:</P>

<OL>
<TT>::</TT><SUB>opt</SUB>&nbsp;<I>nested-name-specifier&nbsp;class-name</I>&nbsp;<TT>::</TT>&nbsp;<TT>~</TT>&nbsp;<I>class-name</I>
</OL>

<P>the <I>class-name</I>s are looked up as types in the scope
designated by the <I>nested-name-specifier</I>.</P>
</BLOCKQUOTE>

<P>This wording doesn't apply, either.  The first one doesn't because
the <I>nested-name-specifier</I> is a <I>class-name</I>, not a
namespace name.  The second doesn't because there's only one layer of
qualification.</P>

<P>As far as I can tell, there's no normative text that specifies how
the <TT>~AB</TT> is looked up in <TT>p-&gt;AB::~AB()</TT>.
3.4.3.1&nbsp;



 <A HREF="basic.html#class.qual">class.qual</A>, where all the other
class member qualified lookups are handled, defers to
3.4.3&nbsp;



 <A HREF="basic.html#basic.lookup.qual">basic.lookup.qual</A>, and 3.4.3&nbsp;



 <A HREF="basic.html#basic.lookup.qual">basic.lookup.qual</A>
doesn't cover the case.</P>

<P>See also <A HREF="
     cwg_defects.html#305">issue 305</A>.</P>

<P>
<U>Jason Merrill</U>:
My thoughts on the subject were that the name we use in a destructor call
is really meaningless; as soon as we see the <TT>~</TT> we know what the
user means,
all we're doing from that point is testing their ability to name the
destructor in a conformant way.  I think that everyone will agree that
<PRE>
  anything::B::~B()
</PRE>
should be well-formed, regardless of the origins of the name "B".  I
believe that the rule about looking up the second "B" in the same context
as the first was intended to provide this behavior, but to me this seems
much more heavyweight than necessary.  We don't need a whole new type of
lookup to be able to use the same name before and after the <TT>~</TT>;
we can just
say that if the two names match, the call is well-formed.  This is
significantly simpler to express, both in the standard and in an
implementation.</P>

<P>Anyone writing two different names here is either deliberately writing
obfuscated code, trying to call the destructor of a nested class, or
fighting an ornery compiler (i.e. one that still wants to see
<TT>B_alias::~B()</TT>).  I think we can ignore the first case.
The third would be
handled by reverting to the old rule (look up the name after <TT>~</TT> in the
normal way) with the lexical matching exception described above -- or we
could decide to break such code, do no lookup at all, and only accept a
matching name.  In a good implementation, the second should probably get an
error message telling them to write <TT>Outer::Inner::~Inner</TT> instead.</P>

<P>We discussed this at the meetings, but I don't remember if we came to
any sort of consensus on a direction.  I see three options:</P>
<OL>
<LI>
Stick with the status quo, i.e. the special lookup rule such that if the
name before <TT>::~</TT> is a class name, the name after <TT>::~</TT>
is looked up in the
same scope as the previous one.  If we choose this option, we just need
better wording that actually expresses this, as suggested in the issue
list.  This option breaks old <TT>B_alias::~B</TT> code where <TT>B_alias</TT>
is declared in a different scope from <TT>B</TT>.
</LI>
<LI>
Revert to the old rules, whereby the name after <TT>::~</TT> is looked up just
like a name after <TT>::</TT>, with the exception that if it matches the name
before <TT>::~</TT> then it is considered to name the same class.  This option
supports old code and code that writes <TT>B_alias::~B_alias</TT>.  It does not
support the <TT>q-&gt;I1::~I2</TT> usage of 3.4.3&nbsp;



 <A HREF="basic.html#basic.lookup.qual">basic.lookup.qual</A>,
but that seems like deliberate
obfuscation.  This option is simpler to implement than #1.
</LI>
<LI>
Do no lookup for a name after <TT>::~</TT>; it must match the
name before.  This
breaks old code as #1, but supports the most important case where the
names match.  This option may be slightly simpler to implement than #2.
It is certainly easier to teach.
</LI>
</OL>

<P>My order of preference is 2, 3, 1.</P>

<P>Incidentally, it seems to me oddly inconsistent to allow
<I>Namespace</I><TT>::~</TT><I>Class</I>,
but not <I>Outer</I><TT>::~</TT><I>Inner</I>.
Prohibiting the latter makes sense from the
standpoint of avoiding ambiguity, but what was the rationale for allowing
the former?</P>

<P>
<U>John Spicer</U>:
I agree that allowing <I>Namespace</I><TT>::~</TT><I>Class</I> is odd.
I'm not sure where this
came from.  If we eliminated that special case, then I believe the #1
rule would just be that in <TT>A::B1::~B2</TT> you look up <TT>B1</TT>
and <TT>B2</TT> in the same place in all cases.</P>

<P>I don't like #2.  I don't think the "old" rules represent a deliberate
design choice, just an error in the way the lookup was described.  The
usage that rule permits <TT>p-&gt;X::~Y</TT>
(where <TT>Y</TT> is a typedef to <TT>X</TT> defined in <TT>X</TT>),
but I doubt people really do that.  In other words, I think that #1
a more useful special case than #2 does, not that I think either special
case is very important.</P>

<P>One problem with the name matching rule is handling cases like:
<PRE>
  A&lt;int&gt; *aip;

  aip-&gt;A&lt;int&gt;::~A&lt;int&gt;();  // should work
  aip-&gt;A&lt;int&gt;::~A&lt;char&gt;(); // should not
</PRE>
I would favor #1, while eliminating the special case of
<I>Namespace</I><TT>::~</TT><I>Class</I>.</P>

<P>
<B>Proposed resolution (10/01):</B>
</P>

<P>Replace the normative text of 3.4.3&nbsp;



 <A HREF="basic.html#basic.lookup.qual">basic.lookup.qual</A> paragraph 5
after the first sentence with:</P>
<BLOCKQUOTE>
<P>Similarly, in a <I>qualified-id</I> of the form:
<PRE>    ::<SUB>opt</SUB> <I>nested-name-specifier</I><SUB>opt</SUB> <I>class-name</I> :: ~ <I>class-name</I>
</PRE>
the second <I>class-name</I> is looked up in the same scope as the first.</P>
</BLOCKQUOTE>
<P>In 12.4&nbsp;



 <A HREF="special.html#class.dtor">class.dtor</A> paragraph 12, change the example to</P>
<BLOCKQUOTE>
<PRE>
D D_object;
typedef B B_alias;
B* B_ptr = &amp;D_object;

void f() {
  D_object.B::~B();                //<I>  calls  </I>B<I>'s destructor</I>
  B_ptr-&gt;~B();                    //<I>  calls  </I>D<I>'s destructor</I>
  B_ptr-&gt;~B_alias();              //<I>  calls  </I>D<I>'s destructor</I>
  B_ptr-&gt;B_alias::~B();           //<I>  calls  </I>B<I>'s destructor</I>
  B_ptr-&gt;B_alias::~B_alias();     //<I>  calls  </I>B<I>'s destructor</I>
}
</PRE>
</BLOCKQUOTE>

<P>
<B>April 2003:</B> See <A HREF="
     cwg_active.html#399">issue 399</A>.</P>

<BR>
<BR>
<HR>
<A NAME="252"></A>
<H4>252.
  
Looking up deallocation functions in virtual destructors
</H4>
<B>Section: </B>12.4&nbsp;



 <A HREF="special.html#class.dtor">class.dtor</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Clamage
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>19 Oct 2000<BR>


<P>[Moved to DR at 10/01 meeting.]</P>



<P>There is a mismatch between 12.4&nbsp;



 <A HREF="special.html#class.dtor">class.dtor</A>
paragraph 11 and 12.5&nbsp;



 <A HREF="special.html#class.free">class.free</A> paragraph 4 regarding
the lookup of deallocation functions in virtual destructors.
12.4&nbsp;



 <A HREF="special.html#class.dtor">class.dtor</A> says,</P>

<BLOCKQUOTE>

At the point of definition of a virtual destructor (including an
implicit definition (12.8&nbsp;



 <A HREF="special.html#class.copy">class.copy</A>)), non-placement
operator delete shall be looked up in the scope of the destructor's
class (3.4.1&nbsp;



 <A HREF="basic.html#basic.lookup.unqual">basic.lookup.unqual</A>) and if found shall be accessible
and unambiguous. [<I>Note</I>: this assures that an operator delete
corresponding to the dynamic type of an object is available for the
<I>delete-expression</I> (12.5&nbsp;



 <A HREF="special.html#class.free">class.free</A>). ]

</BLOCKQUOTE>

<P>The salient features to note from this description are:</P>

<OL>

<LI>The lookup is "in the scope of the destructor's class," which
implies that only members are found (cf 12.2&nbsp;



 <A HREF="special.html#class.temporary">class.temporary</A>).
(The cross-reference would indicate otherwise, however, since it
refers to the description of looking up unqualified names; this kind
of lookup "spills over" into the surrounding scope.)</LI>

<LI>Only non-placement operator delete is looked up.  Presumably
this means that a placement operator delete is ignored in the
lookup.</LI>

</OL>

<P>On the other hand, 12.5&nbsp;



 <A HREF="special.html#class.free">class.free</A> says,</P>

<BLOCKQUOTE>

If a <I>delete-expression</I> begins with a unary <TT>::</TT>
operator, the deallocation function's name is looked up in global
scope. Otherwise, if the <I>delete-expression</I> is used to
deallocate a class object whose static type has a virtual destructor,
the deallocation function is the one found by the lookup in the
definition of the dynamic type's virtual destructor (12.4&nbsp;



 <A HREF="special.html#class.dtor">class.dtor</A>). Otherwise, if the <I>delete-expression</I> is used to
deallocate an object of class <TT>T</TT> or array thereof, the static
and dynamic types of the object shall be identical and the
deallocation function's name is looked up in the scope of
<TT>T</TT>. If this lookup fails to find the name, the name is looked
up in the global scope. If the result of the lookup is ambiguous or
inaccessible, or if the lookup selects a placement deallocation
function, the program is ill-formed.

</BLOCKQUOTE>

<P>Points of interest in this description include:</P>

<OL>

<LI>For a class type with a virtual destructor, the lookup is
described as being "in the definition of the dynamic type's
virtual destructor," rather than "in the scope of the dynamic
type."  That is, the lookup is assumed to be an unqualified
lookup, presumably terminating in the global scope.</LI>

<LI>The assumption is made that the lookup in the virtual
destructor was successful ("...the one found...", not "...the
one found..., <B>if any"</B>).  This will not be the case if
the deallocation function was not declared as a member somewhere
in the inheritance hierarchy.</LI>

<LI>The lookup in the non-virtual-destructor case <B>does</B>
find placement deallocation functions and can fail as a result.</LI>

</OL>

<P>
<B>Suggested resolution:</B> Change the description of the
lookup in 12.4&nbsp;



 <A HREF="special.html#class.dtor">class.dtor</A> paragraph 11 to match the
one in 12.5&nbsp;



 <A HREF="special.html#class.free">class.free</A> paragraph 4.</P>

<P>
<B>Proposed resolution (10/00):</B>
</P>

<OL>

<LI>
<P>Replace 12.4&nbsp;



 <A HREF="special.html#class.dtor">class.dtor</A> paragraph 11 with
the following:</P>

<BLOCKQUOTE>
At the point of definition of a virtual destructor (including an
implicit definition), the non-array deallocation function is looked up
in the scope of the destructor's class (10.2&nbsp;



 <A HREF="derived.html#class.member.lookup">class.member.lookup</A>),
and, if no declaration is found, the function is looked up in the
global scope.  If the result of this lookup is ambiguous or
inaccessible, or if the lookup selects a placement deallocation
function, the program is ill-formed.  [<I>Note:</I> this assures that
a deallocation function corresponding to the dynamic type of an object
is available for the <I>delete-expression</I> (12.5&nbsp;



 <A HREF="special.html#class.free">class.free</A>).]

</BLOCKQUOTE>
</LI>

<LI>
<P>In 12.5&nbsp;



 <A HREF="special.html#class.free">class.free</A> paragraph 4, change</P>

<BLOCKQUOTE>

...the deallocation function is the one found by the lookup in
the definition of the dynamic type's virtual destructor
(12.4&nbsp;



 <A HREF="special.html#class.dtor">class.dtor</A>).

</BLOCKQUOTE>

<P>to</P>

<BLOCKQUOTE>

...the deallocation function is the one selected at the point of
definition of the dynamic type's virtual destructor
(12.4&nbsp;



 <A HREF="special.html#class.dtor">class.dtor</A>).

</BLOCKQUOTE>
</LI>

</OL>

<BR>
<BR>
<HR>
<A NAME="272"></A>
<H4>272.
  
Explicit destructor invocation and <I>qualified-id</I>s
</H4>
<B>Section: </B>12.4&nbsp;



 <A HREF="special.html#class.dtor">class.dtor</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>22 Feb 2001<BR>


<P>[Moved to DR at 10/01 meeting.]</P>

12.4&nbsp;



 <A HREF="special.html#class.dtor">class.dtor</A> paragraph 12 contains the following note:

<BLOCKQUOTE>

an explicit destructor call must always be written using a member
access operator (5.2.5&nbsp;



 <A HREF="expr.html#expr.ref">expr.ref</A>); in particular, the
<I>unary-expression</I> <TT>~X()</TT> in a member function is not an
explicit destructor call (5.3.1&nbsp;



 <A HREF="expr.html#expr.unary.op">expr.unary.op</A>).

</BLOCKQUOTE>

<P>This note is incorrect, as an explicit destructor call can be
written as a <I>qualified-id</I>, e.g., <TT>X::~X()</TT>, which
does not use a member access operator.</P>

<P>
<B>Proposed resolution (04/01):</B>
</P>

<P>Change 12.4&nbsp;



 <A HREF="special.html#class.dtor">class.dtor</A> paragraph 12 as follows:</P>

<BLOCKQUOTE>

[<I>Note:</I> an explicit destructor call must always be written
using a member access operator (5.2.5&nbsp;



 <A HREF="expr.html#expr.ref">expr.ref</A>)
<B>or a <I>qualified-id</I> (5.1&nbsp;



 <A HREF="expr.html#expr.prim">expr.prim</A>)</B>;
in particular, the <I>unary-expression</I> <TT>~X()</TT> in a
member function is not an explicit destructor call
(5.3.1&nbsp;



 <A HREF="expr.html#expr.unary.op">expr.unary.op</A>).]

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="510"></A>
<H4>510.
  
Default initialization of POD classes?
</H4>
<B>Section: </B>12.6&nbsp;



 <A HREF="special.html#class.init">class.init</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>18 Mar 2005<BR>


<P>[Voted into WP at April, 2006 meeting.]</P>

<P>8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A> paragraph 10 makes it clear that
non-static POD class objects with no initializer are left uninitialized
and have an indeterminate initial value:</P>

<BLOCKQUOTE>

If no initializer is specified for an object, and the object is of
(possibly cv-qualified) non-POD class type (or array thereof), the
object shall be default-initialized; if the object is of
const-qualified type, the underlying class type shall have a
user-declared default constructor. Otherwise, if no initializer is
specified for a non-static object, the object and its subobjects, if
any, have an indeterminate initial value; if the object or any of
its subobjects are of const-qualified type, the program is ill-formed.

</BLOCKQUOTE>

<P>12.6&nbsp;



 <A HREF="special.html#class.init">class.init</A> paragraph 1, however, implies that all
class objects without initializers, whether POD or not, are
default-initialized:</P>

<BLOCKQUOTE>

When no initializer is specified for an object of (possibly
cv-qualified) class type (or array thereof), or the initializer has
the form <TT>()</TT>, the object is initialized as specified in
8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A>. The object is default-initialized if there
is no initializer, or value-initialized if the initializer
is <TT>()</TT>.

</BLOCKQUOTE>

<P>
<B>Proposed resolution (October, 2005):</B>
</P>

<P>Remove the indicated words from 12.6&nbsp;



 <A HREF="special.html#class.init">class.init</A> paragraph 1:</P>

<BLOCKQUOTE>

When no initializer is specified for an object of (possibly
cv-qualified) class type (or array thereof), or the initializer has
the form <TT>()</TT>, the object is initialized as specified in
8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A>. <S>The object is default-initialized if
there is no initializer, or value-initialized if the initializer
is <TT>()</TT>.</S>

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="162"></A>
<H4>162.
  
(<TT>&amp;C::f)()</TT> with nonstatic members
</H4>
<B>Section: </B>13.3.1.1&nbsp;



 <A HREF="over.html#over.match.call">over.match.call</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Adamczyk
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>26 Aug 1999<BR>



<P>[Moved to DR at October 2002 meeting.]</P>



<P>13.3.1.1&nbsp;



 <A HREF="over.html#over.match.call">over.match.call</A>
 paragraph 3
says that when a call of the form</P>

<PRE>
   (&amp;C::f)()
</PRE>

is written, the set of overloaded functions named by <TT>C::f</TT>
must not contain
any nonstatic member functions.  A footnote gives the rationale: if a member
of <TT>C::f</TT> is a nonstatic member function,
<TT>&amp;C::f</TT> is a pointer to member
constant, and therefore the call is invalid.

<P>This is clear, it's implementable, and it doesn't directly contradict
anything else in the standard.  However, I'm not sure it's consistent
with some similar cases.</P>

<P>In 13.4&nbsp;



 <A HREF="over.html#over.over">over.over</A>
 paragraph 5,
second example, it is made amply clear that when <TT>&amp;C::f</TT> is
used as the address of a function, e.g.,</P>

<PRE>
   int (*pf)(int) = &amp;C::f;
</PRE>

the overload set can contain both static and nonstatic member functions.
The function with the matching signature is selected, and if it is
nonstatic <TT>&amp;C::f</TT>
is a pointer to member function, and otherwise <TT>&amp;C::f</TT> is
a normal pointer to function.

<P>Similarly, 13.3.1.1.1&nbsp;



 <A HREF="over.html#over.call.func">over.call.func</A>

paragraph 3 makes it clear that</P>

<PRE>
   C::f();
</PRE>

is a valid call even if the overload set contains both static and
nonstatic member functions.  Overload resolution is done, and if a
nonstatic member function is selected, an implicit <TT>this-&gt;</TT> is added,
if that is possible.

<P>Those paragraphs seem to suggest the general rule that you do overload
resolution first and then you interpret the construct you have
according to the function selected.  The fact that there are static
and nonstatic functions in the overload set is irrelevant; it's only
necessary that the chosen function be static or nonstatic to match
the context.</P>

<P>Given that, I think it would be more consistent if the
<TT>(&amp;C::f)()</TT> case
would also do overload resolution first.  If a nonstatic member is
chosen, the program would be ill-formed.</P>

<P>
<B>Proposed resolution (04/01):</B>
</P>

<OL>

<LI>
<P>Change the indicated text in 13.3.1.1&nbsp;



 <A HREF="over.html#over.match.call">over.match.call</A>
paragraph 3:</P>

<BLOCKQUOTE>
The fourth case arises from a <I>postfix-expression</I> of the form
<TT>&amp;F</TT>, where
<TT>F</TT> names  a set of overloaded functions.
In the context of a function call,
<S>the set of functions named by <TT>F</TT> shall contain only non-member
functions and static member functions. [Footnote:
If <TT>F</TT> names a non-static member function, <TT>&amp;F</TT>
is a pointer-to-member, which cannot be used with the function call syntax.]
And in this context using <TT>&amp;F</TT> behaves the same as using</S>
<B><TT>&amp;F</TT> is treated the same as</B>
the name <TT>F</TT> by itself.
Thus, <TT>(&amp;F)(</TT><I>expression-list</I><sub>opt</sub><TT>)</TT>
is simply
<TT>(F)(</TT><I>expression-list</I><sub>opt</sub><TT>)</TT>, which is
discussed in 13.3.1.1.1&nbsp;



 <A HREF="over.html#over.call.func">over.call.func</A>.
<B>If the function selected by overload resolution according to 
13.3.1.1.1&nbsp;



 <A HREF="over.html#over.call.func">over.call.func</A> is
a nonstatic member function, the program is
ill-formed. [Footnote: When <TT>F</TT> is a nonstatic member
function, a reference of the form <TT>&amp;A::F</TT> is a
pointer-to-member,
which cannot be used with the function-call syntax, and
a reference of the form <TT>&amp;F</TT> is an invalid use of the
"<TT>&amp;</TT>" operator on a nonstatic member function.]</B>
(The resolution of <TT>&amp;F</TT> in other contexts is described in
13.4&nbsp;



 <A HREF="over.html#over.over">over.over</A>.)
</BLOCKQUOTE>
</LI>
</OL>

<BR>
<BR>
<HR>
<A NAME="239"></A>
<H4>239.
  
Footnote 116 and Koenig lookup
</H4>
<B>Section: </B>13.3.1.1.1&nbsp;



 <A HREF="over.html#over.call.func">over.call.func</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Clamage
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>2 Aug 2000<BR>


<P>[Moved to DR at 4/01 meeting.]</P>



In describing non-member functions in an overload set, footnote
116 (13.3.1.1.1&nbsp;



 <A HREF="over.html#over.call.func">over.call.func</A>) says,

<BLOCKQUOTE>

Because of the usual name hiding rules, these will be introduced by
declarations or by <i>using-directive</i>s all found in the same block
or all found at namespace scope.

</BLOCKQUOTE>

<P>At least in terms of the current state of the Standard, this
is not correct: a block extern declaration does not prevent
Koenig lookup from occurring.  For example,</P>

<PRE>
    enum E { zero };
    void f(E);
    void g() {
        void f(int);
        f(zero);
    }
</PRE>

<P>In this example, the overload set will include declarations
from both namespace and block scope.</P>

<P>(See also <A HREF="
     cwg_closed.html#12">issue 12</A>.)</P>

<P>
<B>Proposed resolution (04/01):</B>
</P>

<OL>

<LI>
<P>In 3.4.2&nbsp;



 <A HREF="basic.html#basic.lookup.argdep">basic.lookup.argdep</A> paragraph 2, change</P>

<BLOCKQUOTE>

If the ordinary unqualified lookup of the name finds the declaration
of a class member function, the associated namespaces and classes are
not considered.

</BLOCKQUOTE>

<P>to</P>

<BLOCKQUOTE>

If the ordinary unqualified lookup of the name finds the declaration
of a class member function, or a block-scope function declaration
that is not a <I>using-declaration</I>, the associated namespaces
and classes are not considered.

</BLOCKQUOTE>

<P>and change the example to:</P>

<PRE>
    namespace NS {
        class T { };
        void f(T);
        void g(T, int);
    }
    NS::T parm;
    void g(NS::T, float);
    int main() {
        f(parm);            // OK: calls NS::f
        extern void g(NS::T, float);
        g(parm, 1);         // OK: calls g(NS::T, float)
    }
</PRE>

</LI>

<LI>
<P>In 13.3.1.1.1&nbsp;



 <A HREF="over.html#over.call.func">over.call.func</A> paragraph 3 from:</P>

<BLOCKQUOTE>

If the name resolves to a non-member function declaration, that
function and its overloaded declarations constitute the set of
candidate functions.

</BLOCKQUOTE>

<P>to</P>

<BLOCKQUOTE>

If the name resolves to a set of non-member function declarations,
that set of functions constitutes the set of candidate functions.

</BLOCKQUOTE>

<P>Note that this text is also edited by <A HREF="
     cwg_defects.html#364">issue 364</A>.
Also, remove the associated footnote 116.
</P>

</LI>

</OL>

<BR>
<BR>
<HR>
<A NAME="364"></A>
<H4>364.
  
Calling overloaded function with static in set, with no object
</H4>
<B>Section: </B>13.3.1.1.1&nbsp;



 <A HREF="over.html#over.call.func">over.call.func</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Adamczyk
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>23 July 2002<BR>


<P>[Voted into WP at October 2003 meeting.]</P>

<P>Consider this program:</P>
<PRE>
   struct S {
     static void f (int);
     void f (char);
   };

   void g () {
     S::f ('a');
   }
</PRE>
<P>G++ 3.1 rejects it, saying:</P>
<PRE>
   test.C:7: cannot call member function `void S::f(char)' without object
</PRE>

<P>
<U>Mark Mitchell</U>:
It looks to me like G++ is correct, given 13.3.1.1.1&nbsp;



 <A HREF="over.html#over.call.func">over.call.func</A>.
This case is the "unqualified function call" case described in paragraph
3 of that section.  ("Unqualified" here means that there is no "x-&gt;" or
"x." in front of the call, not that the name is unqualified.)</P>

<P>That paragraph says that you first do name lookup.  It then asks you
to look at what declaration is returned.  (That's a bit confusing; you
presumably get a set of declarations.  Or maybe not; the name lookup
section says that if name lookup finds a non-static member in a context
like this the program is in error.  But surely this program is not
erroneous.  Hmm.)</P>

<P>Anyhow, you have -- at least -- "S::f(char)" as the result of the
lookup.</P>

<P>The keyword "this" is not in scope, so "all overloaded declarations of
the function name in T become candidate functions and a contrived object
of type T becomes the implied object argument."  That means we get
both  versions of "f" at this point.  Then, "the call is ill-formed,
however, if overload resolution selects one of the non-static members
of T in this case."  Since, in this case, "S::f(char)" is the winner,
the program is ill-formed.</P>

<P>
<U>Steve Adamczyk</U>:
This result is surprising, because we've selected a function
that we cannot call, when there is another function that can be
called.  This should either be ambiguous, or it should select the static
member function.  See also 13.3.1&nbsp;



 <A HREF="over.html#over.match.funcs">over.match.funcs</A> paragraph 2:
"Similarly, when
appropriate, the context can construct an argument list that
contains an implied object argument..."</P>

<P>
<B>Notes from October 2002 meeting:</B>
</P>

<P>We agreed that g++ has it right, but the standard needs to be clearer.</P>

<P>
<B>Proposed resolution (October 2002, revised April 2003):</B>
</P>

<P>Change 13.3.1.1.1&nbsp;



 <A HREF="over.html#over.call.func">over.call.func</A> paragraphs 2 and 3 as
follows:</P>
<BLOCKQUOTE>
<P>In qualified function calls, the name to be resolved is an
<I>id-expression</I> and is preceded by an <TT>-&gt;</TT> or <TT>.</TT>
operator. Since the construct <TT>A-&gt;B</TT> is generally equivalent
to <TT>(*A).B</TT>, the rest of clause 13&nbsp;



 <A HREF="over.html#over">over</A>
assumes, without loss of generality, that all member function calls have been 
normalized to the form that uses an object and the <TT>.</TT> operator. 
Furthermore, clause 13&nbsp;



 <A HREF="over.html#over">over</A>
assumes that the <I>postfix-expression</I> that is the left
operand of the <TT>.</TT> operator has type ``<I>cv</I> <TT>T</TT>''
where <TT>T</TT> denotes a class.
[Footnote: Note that cv-qualifiers on the type of 
objects are significant in overload resolution for both lvalue and
class rvalue objects. --- end footnote]
Under this assumption, the <I>id-expression</I> in the 
call is looked up as a member function of <TT>T</TT> following the rules for 
looking up names in classes (10.2&nbsp;



 <A HREF="derived.html#class.member.lookup">class.member.lookup</A>).
<S>If a member function is found, that function and its overloaded 
declarations</S> <B>The function declarations found by that lookup</B>
constitute the set of candidate functions. The argument list is the
<I>expression-list</I> in the call augmented by the addition of the
left operand of the <TT>.</TT> operator in the normalized member
function call as the implied object argument (13.3.1&nbsp;



 <A HREF="over.html#over.match.funcs">over.match.funcs</A>).
</P>
<P>In unqualified function calls, the name is 
not qualified by an <TT>-&gt;</TT> or <TT>.</TT> operator and has the more 
general form of a <I>primary-expression</I>. The name is looked up in the 
context of the function call following the normal rules for name lookup in 
function calls (<S>3.4.2&nbsp;



 <A HREF="basic.html#basic.lookup.argdep">basic.lookup.argdep</A></S>
3.4&nbsp;



 <A HREF="basic.html#basic.lookup">basic.lookup</A>).
<S>If the name resolves to a non-member function declaration, that
function and its overloaded declarations</S>
<B>The function declarations found by that lookup</B>
constitute the set of candidate functions.
<S>[Footnote: Because of the usual name hiding rules, 
these will be introduced by declarations or by <I>using-directive</I>s all 
found in the same block or all found at namespace scope. --- end footnote]</S>
<B>Because of the rules for name lookup,
the set of candidate functions consists (1) entirely of non-member functions
or (2) entirely of member functions of some class </B><TT><B>T</B></TT><B>. In 
case (1), t</B><S>T</S>he argument list is the same as
the <I>expression-list</I> in the call.
<S>If the name resolves to a nonstatic member function, then the 
function call is actually a member function call.</S>
<B>In case (2), the argument list is the <I>expression-list</I> in the
call augmented by the addition of an implied object argument as in
a qualified function call.</B> 
If the keyword <TT>this</TT> (9.3.2&nbsp;



 <A HREF="class.html#class.this">class.this</A>) 
is in scope and refers to <S>the </S>class <TT><B>T</B></TT> <S>of that member 
function</S>, or a derived class <S>thereof</S> <B>of <TT>T</TT></B>, then 
the <S>function call is transformed into a normalized qualified
function call using</S>
<B>implied object argument is</B><TT>(*this)</TT> <S>as the
<I>postfix-expression</I>
to the left of the <TT>.</TT> operator</S>. <S>The candidate 
functions and argument list are as described for qualified function calls 
above.</S> If the keyword <TT>this</TT> is not in scope or refers to 
another class, then <S>name resolution found a static member of some
class </S><TT><S>T</S></TT><S>. 
In this case,</S> <S>all overloaded declarations of the function name in
<TT>T</TT> become candidate functions and</S> a contrived object of 
type <TT>T</TT> becomes the implied object argument.
[Footnote: An implied object argument must be 
contrived to correspond to the implicit object parameter attributed to member 
functions during overload resolution. It is not used in the call to the 
selected function. Since the member functions all have the same implicit
object 
parameter, the contrived object will not be the cause to select or reject a 
function. --- end footnote]
<B>If the argument list is augmented by a contrived object 
and </B><S>The call is ill-formed, however, if</S> overload 
resolution selects one of the non-static member functions of
<TT>T</TT><B>, the 
call is ill-formed</B><S> in this case</S>.
</P>
</BLOCKQUOTE>

<P>Note that <A HREF="
     cwg_defects.html#239">issue 239</A> also edits
paragraph 3.</P>

<BR>
<BR>
<HR>
<A NAME="280"></A>
<H4>280.
  
Access and surrogate call functions
</H4>
<B>Section: </B>13.3.1.1.2&nbsp;



 <A HREF="over.html#over.call.object">over.call.object</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Andrei Iltchenko
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>16 Apr 2001<BR>


<P>[Voted into WP at October 2003 meeting.]</P>

<P>According to 13.3.1.1.2&nbsp;



 <A HREF="over.html#over.call.object">over.call.object</A> paragraph 2, when
the <I>primary-expression</I> <TT>E</TT> in the function call syntax
evaluates to a class object of type "<I>cv</I> <TT>T</TT>", a
surrogate call function corresponding to an appropriate conversion
function declared in a direct or indirect base class <TT>B</TT> of
<TT>T</TT> is included or not included in the set of candidate
functions based on class <TT>B</TT> being accessible.</P>

<P>For instance in the following code sample, as per the paragraph in
question, the expression <TT>c(3)</TT> calls <TT>f2</TT>, instead of
the construct being ill-formed due to the conversion function
<TT>A::operator fp1</TT> being inaccessible and its corresponding
surrogate call function providing a better match than the surrogate
call function corresponding to <TT>C::operator fp2</TT>:</P>

<PRE>
    void  f1(int)  {   }
    void  f2(float)  {   }
    typedef void  (* fp1)(int);
    typedef void  (* fp2)(float);

    struct  A  {
       operator fp1()
       {   return  f1;   }
    };

    struct  B :  private A  {   };

    struct  C :  B  {
       operator  fp2()
       {   return  f2;   }
    };

    int  main()
    {
       C   c;
       c(3);  // f2 is called, instead of the construct being ill-formed.
       return  0;
    }
</PRE>

<P>The fact that the accessibility of a base class influences the
overload resolution process contradicts the fundamental language rule
(3.4&nbsp;



 <A HREF="basic.html#basic.lookup">basic.lookup</A> paragraph 1, and 13.3&nbsp;



 <A HREF="over.html#over.match">over.match</A> paragraph 2) that access checks are applied only once
name lookup and function overload resolution (if applicable) have
succeeded.</P>

<P>
<B>Notes from 4/02 meeting:</B>
</P>

<P>There was some concern about whether 10.2&nbsp;



 <A HREF="derived.html#class.member.lookup">class.member.lookup</A> (or
anything else, for that matter) actually defines "ambiguous base class".
See <A HREF="
     cwg_defects.html#39">issue 39</A>.  See also
<A HREF="
     cwg_active.html#156">issue 156</A>.</P>

<P>
<B>Notes from October 2002 meeting:</B>
</P>

<P>It was suggested that the ambiguity check is done as part of the
call of the conversion function.</P>

<P>
<B>Proposed resolution (revised October 2002):</B>
</P>

<P>In 13.3.1.1.2&nbsp;



 <A HREF="over.html#over.call.object">over.call.object</A> paragraph 2, replace the
last sentence</P>

<BLOCKQUOTE>

Similarly, surrogate call functions are added to the set of candidate
functions for each conversion function declared in an accessible base
class provided the function is not hidden within <TT>T</TT> by another
intervening declaration.

</BLOCKQUOTE>

<P>with</P>

<BLOCKQUOTE>

Similarly, surrogate call functions are added to the set of candidate
functions for each conversion function declared in a base class of
<TT>T</TT> provided the function is not hidden within <TT>T</TT> by
another intervening declaration.
</BLOCKQUOTE>

<P>Replace 13.3.1.1.2&nbsp;



 <A HREF="over.html#over.call.object">over.call.object</A> paragraph 3
<BLOCKQUOTE>
If  such a surrogate call function is selected by overload resolution,
its body, as defined above, will be  executed  to  convert  <TT>E</TT>  to  the
appropriate  function  and then to invoke that function with the
arguments of the call.
</BLOCKQUOTE>
by
<BLOCKQUOTE>
If  such a surrogate call function is selected by overload resolution,
the corresponding conversion function will be called to convert
<TT>E</TT>  to  the appropriate  function pointer or reference,
and the function will then be invoked with the  arguments of the call.
If the conversion function cannot be called
(e.g., because of an ambiguity), the program is ill-formed.
</BLOCKQUOTE>
</P>

<BR>
<BR>
<HR>
<A NAME="416"></A>
<H4>416.
  
Class must be complete to allow operator lookup?
</H4>
<B>Section: </B>13.3.1.2&nbsp;



 <A HREF="over.html#over.match.oper">over.match.oper</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Greg Comeau
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>22 May 2003<BR>


<P>[Voted into WP at October 2004 meeting.]</P>

<P>Normally reference semantics allow incomplete types in certain contexts,
but isn't this:</P>
<PRE>
  class A;

  A&amp; operator&lt;&lt;(A&amp; a, const char* msg);
  void foo(A&amp; a)
  {
    a &lt;&lt; "Hello";
  }
</PRE>
<P>required to be diagnosed because of the op&lt;&lt;? The reason
being that the class may actually have an op&lt;&lt;(const char *) in it.</P>

<P>What is it?   un- or ill-something?   Diagnosable?   No problem at all?</P>

<P>
<U>Steve Adamczyk:</U>
I don't know of any requirement in the standard that the class be complete.
There is a rule that will instantiate a class template in order to be able
to see whether it has any operators.  But I wouldn't think one wants to
outlaw the above example merely because the user might have an
operator&lt;&lt;
in the class; if he doesn't, he would not be pleased that the above
is considered invalid.</P>

<P>
<U>Mike Miller:</U>
Hmm, interesting question.  My initial reaction is that it just
uses <TT>::operator&lt;&lt;</TT>; any <TT>A::operator&lt;&lt;</TT>
simply won't be considered in
overload resolution.  I can't find anything in the Standard that
would say any different.</P>

<P>The closest analogy to this situation, I'd guess, would be
deleting a pointer to an incomplete class;
5.3.5&nbsp;



 <A HREF="expr.html#expr.delete">expr.delete</A> paragraph 5 says that that's
undefined behavior if the complete type has a non-trivial destructor
or an operator delete.  However, I tend to think that that's because
it deals with storage and resource management, not just because it
might have called a different function.  Generally, overload
resolution that goes one way when it might have gone another with
more declarations in scope is considered to be not an error, cf
7.3.3&nbsp;



 <A HREF="dcl.html#namespace.udecl">namespace.udecl</A> paragraph 9,
14.6.3&nbsp;



 <A HREF="template.html#temp.nondep">temp.nondep</A> paragraph 1, etc.</P>

<P>So my bottom line take on it would be that it's okay, it's up to
the programmer to ensure that all necessary declarations are in
scope for overload resolution.  Worst case, it would be like the
operator delete in an incomplete class -- undefined behavior, and
thus not required to be diagnosed.</P>

<P>13.3.1.2&nbsp;



 <A HREF="over.html#over.match.oper">over.match.oper</A> paragraph 3, bullet 1, says,
"If T1 is a class type, the set of member candidates is the result
of the qualified lookup of <TT>T1::operator@</TT>
(13.3.1.1.1&nbsp;



 <A HREF="over.html#over.call.func">over.call.func</A>)."  Obviously, that lookup is
not possible if T1 is
incomplete.  Should 
13.3.1.2&nbsp;



 <A HREF="over.html#over.match.oper">over.match.oper</A> paragraph 3, bullet 1, say
"complete class type"?  Or does the inability to perform
the lookup mean that the program is ill-formed?
3.2&nbsp;



 <A HREF="basic.html#basic.def.odr">basic.def.odr</A> paragraph 4 doesn't apply,
I don't think, because you don't know whether you'll be applying a
class member access operator until you know whether the operator
involved is a member or not.</P>

<P>
<B>Notes from October 2003 meeting:</B>
</P>

<P>We noticed that the title of this issue did not match the
body.  We checked the original source and then corrected the title
(so it no longer mentions templates).</P>

<P>We decided that this is similar to other cases like
deleting a pointer to an incomplete class, and it should not be
necessary to have a complete class.  There is no undefined
behavior.</P>

<P>
<B>Proposed Resolution (October 2003):</B>
</P>

<P>Change the first bullet of 13.3.1.2&nbsp;



 <A HREF="over.html#over.match.oper">over.match.oper</A> paragraph 3
to read:</P>
<BLOCKQUOTE>
If T1 is a <B>complete</B> class type, the set of member candidates
is the result of the qualified lookup of <TT>T1::operator@</TT>
(13.3.1.1.1&nbsp;



 <A HREF="over.html#over.call.func">over.call.func</A>); otherwise, the set of member
candidates is empty.
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="60"></A>
<H4>60.
  
Reference binding and valid conversion sequences
</H4>
<B>Section: </B>13.3.3.1.4&nbsp;



 <A HREF="over.html#over.ics.ref">over.ics.ref</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Adamczyk
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>13 Oct 1998<BR>



<P>[Moved to DR at October 2002 meeting.]</P>

<P>Does dropping a cv-qualifier on a reference binding prevent the binding
as far as overload resolution is concerned?
Paragraph 4 says "Other restrictions
on binding a reference to a particular argument do not affect the formation
of a conversion sequence."  This was intended to refer to things like access
checking, but some readers have taken that to mean that any aspects of
reference binding not mentioned in this section do not preclude the binding.</P>

<P>
<B>Proposed resolution (10/01):</B>
</P>

<P>In 13.3.3.1.4&nbsp;



 <A HREF="over.html#over.ics.ref">over.ics.ref</A> paragraph 4 add the
indicated text:</P>
<BLOCKQUOTE>
Other restrictions on binding a reference to a particular argument <B>that
are not based on the types of the reference and the argument</B> do
not  affect  the formation of a standard conversion sequence, however.
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="115"></A>
<H4>115.
  
Address of template-id
</H4>
<B>Section: </B>13.4&nbsp;



 <A HREF="over.html#over.over">over.over</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>John Spicer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>7 May 1999<BR>



<P>[Voted into WP at October 2003 meeting.]</P>



<PRE>
    template &lt;class T&gt; void f(T);
    template &lt;class T&gt; void g(T);
    template &lt;class T&gt; void g(T,T);

    int main()
    {
        (&amp;f&lt;int&gt;);
        (&amp;g&lt;int&gt;);
    }
</PRE>

The question is whether <TT>&amp;f&lt;int&gt;</TT> identifies a unique function.
<TT>&amp;g&lt;int&gt;</TT> is clearly ambiguous.

<P>13.4&nbsp;



 <A HREF="over.html#over.over">over.over</A>
 paragraph 1
says that a function template name is considered to name a
set of overloaded functions.  I believe it should be expanded to say that
a function template name with an explicit template argument list is also
considered to name a set of overloaded functions.</P>

<P>In the general case, you need to have a destination type in order
to identify a unique function.  While it is possible to permit this, I
don't think it is a good idea because such code depends on there only
being one template of that name that is visible.</P>

<P>The EDG front end issues an error on this use of "<TT>f</TT>".
egcs 1.1.1 allows
it, but the most current snapshot of egcs that I have also issues an error
on it.</P>

<P>It has been pointed out that when dealing with nontemplates, the rules
for taking the address of a single function differ from the rules
for an overload set, but this asymmetry is needed for C compatibility.
This need does not exist for the template case.</P>

<P>My feeling is that a general rule is better than a general rule plus
an exception.  The general rule is that you need a destination type
to be sure that the operation will succeed.  The exception is when
there is only one template in the set and only then when you provide
values for all of the template arguments.</P>

<P>It is true that in some cases you can provide a shorthand, but only if
you encourage a fragile coding style (that will cause programs to break
when additional templates are added).</P>

<P>I think the standard needs to specify one way or the other how this
case should be handled.  My recommendation would be that it is
ill-formed.</P>

<P>
<U>Nico Josuttis</U>: Consider the following example:</P>

<PRE>
    template &lt;int VAL&gt;
    int add (int elem)
    {
	return elem + VAL;
    }

    std::transform(coll.begin(), coll.end(),
		   coll.begin(),
		   add&lt;10&gt;);
</PRE>

<P>If John's recommendation is adopted, this code will become
ill-formed.  I bet there will be a lot of explanation for users
necessary why this fails and that they have to change
<TT>add&lt;10&gt;</TT> to something like
<TT>(int (*)(int))add&lt;10&gt;</TT>.</P>

<P>This example code is probably common practice because this
use of the STL is typical and is accepted in many current
implementations.  I strongly urge that this issue be resolved
in favor of keeping this code valid.</P>

<P>
<U>Bill Gibbons</U>:  I find this rather surprising.  Shouldn't
a <I>template-id</I> which specifies all of the template arguments
be treated like a declaration-only explicit instantiation,
producing a set of ordinary function declarations?  And when that
set happens to contain only one function, shouldn't the example
code work?</P>

<P>(See also <A HREF="
     cwg_defects.html#250">issue 250</A>.)</P>

<P>
<B>Notes from 04/01 meeting:</B>
</P>

<P>The consensus of the group was that the <TT>add</TT> example
should not be an error.</P>

<P>
<B>Proposed resolution (October 2002):</B>
</P>

<P>In 13.4 add to the end of paragraph 2:</P>
<BLOCKQUOTE>
[<I>Note:</I> As described in 14.8.1&nbsp;



 <A HREF="template.html#temp.arg.explicit">temp.arg.explicit</A>,
if deduction fails and the
function template name is followed by an explicit template
argument list, the <I>template-id</I> is then examined to
see whether it identifies a single function template
specialization.  If it does, the <I>template-id</I> is
considered to be an lvalue for that function template
specialization.  The target type is not used in that
determination.]
</BLOCKQUOTE>

<P>
In 14.8.1&nbsp;



 <A HREF="template.html#temp.arg.explicit">temp.arg.explicit</A> paragraph 2 insert before
the first example:</P>
<BLOCKQUOTE>
In contexts where deduction is done and fails,
or in contexts where deduction is not done,
if a template argument list is specified and it, along with any
default template arguments, identifies a single function template
specialization, then the <I>template-id</I> is an lvalue
for the function template specialization.
</BLOCKQUOTE>

<P>
Change the first example of 14.8.1&nbsp;



 <A HREF="template.html#temp.arg.explicit">temp.arg.explicit</A> paragraph 2:</P>
<PRE>
  template&lt;class X, class Y&gt; X f(Y);
  void g()
  {
    int i = f&lt;int&gt;(5.6);    // Y <I>is deduced to be</I> double
    int j = f(5.6);         // <I>ill-formed:</I> X <I>cannot be deduced</I>
  }
</PRE>
to read:
<PRE>
  template&lt;class X, class Y&gt; X f(Y);
  void g()
  {
    int i = f&lt;int&gt;(5.6);    // Y <I>is deduced to be</I> double
    int j = f(5.6);         // <I>ill-formed:</I> X <I>cannot be deduced</I>
    f&lt;void&gt;(f&lt;int, bool&gt;);  // Y <I>for outer</I> f <I>deduced to be</I>
                            //   int (*)(bool)
    f&lt;void&gt;(f&lt;int&gt;);        // <I>ill-formed:</I> f&lt;int&gt; <I>does not denote a</I>
                            //   <I>single template function specialization</I>
  }
</PRE>

<P>
<B>Note:</B> This interacts with the resolution of
<A HREF="
     cwg_defects.html#226">issue 226</A> (default
template arguments for function templates).
</P>

<BR>
<BR>
<HR>
<A NAME="221"></A>
<H4>221.
  
Must compound assignment operators be member functions?
</H4>
<B>Section: </B>13.5.3&nbsp;



 <A HREF="over.html#over.ass">over.ass</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Jim Hyslop
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>3 Apr 2000<BR>


<P>[Moved to DR at 4/01 meeting.]</P>

<P>Is the intent of 13.5.3&nbsp;



 <A HREF="over.html#over.ass">over.ass</A> paragraph 1 that
<I>all</I> assignment operators be non-static member functions
(including <TT>operator+=</TT>, <TT>operator*=</TT>, etc.) or only
simple assignment operators (<TT>operator=</TT>)?</P>

<P>
<B>Notes from 04/00 meeting:</B>
</P>

<P>Nearly all references to "assignment operator" in the IS mean
<TT>operator=</TT> and not the compound assignment operators.  The ARM
was specific that this restriction applied only to <TT>operator=</TT>.
If it did apply to compound assignment operators, it would be
impossible to overload these operators for <TT>bool</TT> operands.</P>

<P>
<B>Proposed resolution (04/01):</B>
</P>

<OL>
<LI>
<P>Change the title of 5.17&nbsp;



 <A HREF="expr.html#expr.ass">expr.ass</A> from "Assignment
operators" to "Assignment and compound assignment operators."</P>
</LI>

<LI>
<P>Change the first sentence of 5.17&nbsp;



 <A HREF="expr.html#expr.ass">expr.ass</A>
paragraph 1 from</P>
<BLOCKQUOTE>

There are several assignment operators, all of which group
right-to-left.  All require a modifiable lvalue as their left operand,
and the type of an assignment expression is that of its left operand.
The result of the assignment operation is the value stored in the left
operand after the assignment has taken place; the result is an lvalue.

</BLOCKQUOTE>

<P>to</P>

<BLOCKQUOTE>

The assignment operator (<TT>=</TT>) and the compound assignment
operators all group right-to-left.  All require a modifiable lvalue as
their left operand and return an lvalue with the type and value of
the left operand after the assignment has taken place.

</BLOCKQUOTE>
</LI>
</OL>

<P>
<B>Additional note (10/00):</B> Paragraphs 2-6 of
5.17&nbsp;



 <A HREF="expr.html#expr.ass">expr.ass</A> should all be understood to apply to
simple assignment only and not to compound assignment operators.</P>

<BR>
<BR>
<HR>
<A NAME="420"></A>
<H4>420.
  
postfixexpression-&gt;scalar_type_dtor() inconsistent
</H4>
<B>Section: </B>13.5.6&nbsp;



 <A HREF="over.html#over.ref">over.ref</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Markus Mauhart
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>8 June 2003<BR>


<P>[Voted into WP at April, 2006 meeting.]</P>

<P>Lets start with the proposed solution.
In 13.5.6&nbsp;



 <A HREF="over.html#over.ref">over.ref</A>, replace line ...
<BLOCKQUOTE>
<I>postfix-expression</I> <TT>-&gt;</TT> <I>id-expression</I>
</BLOCKQUOTE>
.... with the lines ...
<BLOCKQUOTE>
<I>postfix-expression</I> <TT>-&gt;</TT> <I>template<SUB>opt</SUB> id-expression</I>
<BR>
<I>postfix-expression</I> <TT>-&gt;</TT> <I>pseudo-destructor-name</I>
</BLOCKQUOTE>
(This then is a copy of the two lines in 5.2&nbsp;



 <A HREF="expr.html#expr.post">expr.post</A>
covering "-&gt;dtor")</P>
<P>Alternatively remove the sentence "It implements class member
access using -&gt;" and the syntax line following.</P>

<P>Reasons:</P>

<P>Currently stdc++ is inconsistent when handling expressions of
the form "postfixexpression-&gt;scalar_type_dtor()":
If "postfixexpression" is a pointer to the scalar type, it is OK,
but if "postfixexpression" refers to any smart pointer class
(e.g. iterator or allocator::pointer) with class specific
CLASS::operator-&gt;() returning pointer to the scalar type, then
it is ill-formed; so while c++98 does allow CLASS::operator-&gt;()
returning pointer to scalar type, c++98 prohibits any '-&gt;'-expression
involving this overloaded operator function.</P>

<P>Not only is this behaviour inconsistent, but also when
comparing the corresponding chapters of c++pl2 and stdc++98
it looks like an oversight and unintended result.
Mapping between stdc++98 and c++pl2:
<BLOCKQUOTE>
  c++pl2.r.5.2 -&gt; 5.2 [expr.post]<BR>
  c++pl2.r.5.2.4 -&gt; 5.2.4 [expr.pseudo] + 5.2.5 [expr.ref]<BR>
  c++pl2.r.13.4 -&gt; 13.3.1.2 [over.match.oper]<BR>
  c++pl2.r.13.4.6 -&gt; 13.5.6 [over.ref]
</BLOCKQUOTE>
For the single line of c++pl2.r.5.2 covering "-&gt;dtor",
5.2 [expr.post] has two lines.
Analogously c++pl2.r.5.2.4 has been doubled to 5.2.4 [expr.pseudo]
and 5.2.5 [expr.ref].
From 13.5.6 [over.ref], the sentence forbiding CLASS::operator-&gt;()
returning pointer to scalar type has been removed.
Only the single line of c++pl2.r.13.4.6 (&lt;-&gt; c++pl2.r.5.2's
single line) has not gotten its 2nd line when converted
into 13.5.6 [over.ref].</P>

<P>Additionally GCC32 does is right (but against 13.5.6 [over.ref]).</P>

<P>AFAICS this would not break old code except compilers like VC7x
and Comeau4301.</P>

<P>It does not add new functionality, cause any expression
class_type-&gt;scalar_type_dtor() even today can be substituted
through (*class_type).scalar_type_dtor().</P>

<P>Without this fix, template functions like
some_allocator&lt;T&gt;::destroy(p)
must use "(*p).~T()" or "(*p).T::~T()" when calling the destructor,
otherwise the simpler versions "p-&gt;~T()" or "p-&gt;T::~T()"
could be used.</P>

<P>Sample code, compiled with GCC32, VC7[1] and Comeau4301:</P>
<PRE>
struct A {};//any class

template &lt;class T&gt;
struct PTR
    {
    T&amp; operator*  () const;
    T* operator-&gt; () const;
    };

template &lt;class T&gt;
void f ()
    {
        {
        T*  p               ;
        p = new T           ;
        (*p).T::~T()        ;//OK
        p = new T           ;
        (*p).~T()           ;//OK
        p = new T           ;
        p-&gt;T::~T()          ;//OK
        p = new T           ;
        p-&gt;~T()             ;//OK
        }

        {
        PTR&lt;T&gt; p = PTR&lt;T&gt;() ;
        (*p).T::~T()        ;//OK
        (*p).~T()           ;//OK
        p.operator-&gt;()      ;//OK !!!
        p-&gt;T::~T()          ;//GCC32: OK; VC7x,Com4301: OK for A; ERROR w/ int
        p-&gt;~T()             ;//GCC32: OK; VC7x,Com4301: OK for A; ERROR w/ int
        }
    }

void test ()
    {
    f &lt;A&gt;  ();
    f &lt;int&gt;();
    }
</PRE>

<P>
<B>Proposed resolution (April, 2005):</B>
</P>

<P>Change 13.5.6&nbsp;



 <A HREF="over.html#over.ref">over.ref</A> paragraph 1 as indicated:</P>

<BLOCKQUOTE>

<P>
<TT>operator-&gt;</TT> shall be a non-static member function taking
no parameters. It implements <B>the</B> class member
access <S>using</S> <B>syntax that uses</B> <TT>-&gt;</TT>
</P>

<UL>
<I>postfix-expression</I> <TT>-&gt;</TT> <B><TT>template</TT><SUB><I><SMALL>opt</SMALL></I></SUB></B> <I>id-expression</I>
<BR>
<B><I>postfix-expression</I> <TT>-&gt;</TT> <I>pseudo-destructor-name</I></B>
</UL>

<P>An expression <TT>x-&gt;m</TT> is interpreted
as <TT>(x.operator-&gt;())-&gt;m</TT> for a class object <TT>x</TT> of
type <TT>T</TT> if <TT>T::operator-&gt;()</TT> exists and if the
operator is selected as the best match function by the overload
resolution mechanism (13.3&nbsp;



 <A HREF="over.html#over.match">over.match</A>).</P>

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="425"></A>
<H4>425.
  
Set of candidates for overloaded built-in operator with float operand
</H4>
<B>Section: </B>13.6&nbsp;



 <A HREF="over.html#over.built">over.built</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Daniel Frey
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>30 June 2003<BR>


<P>[Voted into WP at March 2004 meeting.]</P>



<P>During a discussion over at the boost mailing list (www.boost.org), we
came across the following "puzzle":</P>
<PRE>
  struct A {
    template&lt; typename T &gt; operator T() const;
  } a;

  template&lt;&gt; A::operator float() const
  {
    return 1.0f;
  }

  int main()
  {
    float f = 1.0f * a;
  }
</PRE>
<P>The code is compiled without errors or warnings from EDG-based compilers
(Comeau, Intel), but rejected from others (GCC, MSVC [7.1]). The
question: Who is correct? Where should I file the bug report?</P>

<P>To explain the problem: The EDG seems to see 1.0f*a as a call to the
unambiguous operator*(float,float) and thus casts 'a' to 'float'. The
other compilers have several operators (float*float, float*double,
float*int, ...) available and thus can't decide which cast is
appropriate. I think the latter is the correct behaviour, but I'd like
to hear some comments from the language lawyers about the standard's
point of view on this problem.</P>

<P>
<U>Andreas Hommel:</U>
Our compiler also rejects this code:</P>
<PRE>
Error   : function call 'operator*(float, {lval} A)' is ambiguous
'operator*(float, unsigned long long)'
'operator*(float, int)'
'operator*(float, unsigned int)'
'operator*(float, long)'
'operator*(float, unsigned long)'
'operator*(float, float)'
'operator*(float, double)'
'operator*(float, long double)'
'operator*(float, long long)'
Test.cp line 12       float f = 1.0f * a;
</PRE>
<P>Is this example really legal? It was my understanding that all candidates
from 13.6&nbsp;



 <A HREF="over.html#over.built">over.built</A> participate in overload resolution.</P>

<P>
<U>Daveed Vandevoorde:</U>
I believe the EDG-based compiler is right.  Note that the built-in operator*
requires "usual arithmetic conversions" (see
5.6&nbsp;



 <A HREF="expr.html#expr.mul">expr.mul</A> paragraph 2 and
5&nbsp;



 <A HREF="expr.html#expr">expr</A> paragaph 9). This means that
there is no candidate taking (float, double) arguments: Only (float, float)
or
(double, double).</P>

<P>Since your first argument is of type float, the (float, float) case is
preferred
over the (double, double) case (the latter would require a floating-point
promotion).</P>

<P>
<U>Stave Adamczyk:</U>
Daveed's statement is wrong; as Andreas says, the prototypes in
13.6&nbsp;



 <A HREF="over.html#over.built">over.built</A> paragraph 12
have pairs of types, not the same type twice.  However, the list of
possibilities considered in Andreas' message is wrong also:
13.6&nbsp;



 <A HREF="over.html#over.built">over.built</A> paragraph 12
calls for pairs of <B>promoted</B> arithmetic types, and float is not
a promoted type (it promotes to double -- see
4.6&nbsp;



 <A HREF="conv.html#conv.fpprom">conv.fpprom</A>).</P>

<P>Nevertheless, the example is ambiguous.  Let's look at the overload
resolution costs.  The right operand is always going to have a
user-defined-conversion cost (the template conversion function
will convert directly to the const version of the second
parameter of the prototype).  The left operand is always going to
have a promotion (float --&gt; double) or a standard conversion
(anything else).  So the cases with promotions are better 
than the others.  However, there are several of those
cases, with second parameters of type int, unsigned int, long,
unsigned long, double, and long double, and all of those are
equally good.  Therefore the example is ambiguous.</P>

<P>Here's a reduced version that should be equivalent:</P>
<PRE>
  struct A {
    template &lt;typename T&gt; operator T() const;
  } a;
  void f(double, int);
  void f(double, unsigned int);
  void f(double, long);
  void f(double, unsigned long);
  void f(double, double);
  void f(double, long double);
  int main() {
    f(1.0f, a);  // Ambiguous
  }
</PRE>
<P>Personally, I think this is evidence that
13.6&nbsp;



 <A HREF="over.html#over.built">over.built</A> doesn't really
do quite what it should.  But the standard is clear, if possibly
flawed.</P>

<P>
<U>Andreas Hommel:</U>
You are right, "float" is not a promoted arithmetic type, this is a bug in
our compiler.</P>

<P>However, the usual arithmetic conversions
(5&nbsp;



 <A HREF="expr.html#expr">expr</A> paragraph 9) do not promote the floating
point types, so
<PRE>
  float operator+(float, float);
</PRE>
is a legal built-in operator function, so I wonder if it shouldn't be
included in the candidate list.</P>

<P>
<U>Steve Adamczyk:</U> Hmm, the definition of the term in
13.6&nbsp;



 <A HREF="over.html#over.built">over.built</A> paragraph 2 is highly ambiguous:
<BLOCKQUOTE>
  Similarly, the  term  promoted  arithmetic type refers to promoted 
  integral types plus floating types.
</BLOCKQUOTE>
I can't tell if that's "promoted integral types plus (all) floating
types" or "promoted integral types plus (promoted) floating types".
I thought the latter was intended, but indeed the usual arithmetic
conversions could give you "float + float", so it makes sense that
float would be one of the possibilities.  We should discuss this to
make sure everyone has the same interpretation.</P>

<P>
<B>Proposed Resolution (October 2003):</B>
</P>

<P>Change the second sentence of 13.6 paragraph 2 as follows:</P>
<BLOCKQUOTE>
Similarly, the term <I>promoted arithmetic type</I> refers
to <S>promoted integral types plus floating types</S>
<B>floating types plus promoted integral types</B>.
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="204"></A>
<H4>204.
  
Exported class templates
</H4>
<B>Section: </B>14&nbsp;



 <A HREF="template.html#temp">temp</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Robert Klarer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>11 Feb 2000<BR>



<P>[Voted into WP at April 2003 meeting.]</P>

<P>14&nbsp;



 <A HREF="template.html#temp">temp</A>
 paragraph 7 allows class
templates to be declared exported, including member classes and member
class templates (implicitly by virtue of exporting the
containing template class).  However, paragraph 8 does not exclude
exported class templates from the statement that</P>

<BLOCKQUOTE>
An exported template need only be declared (and not necessarily
defined) in a translation unit in which it is instantiated.
</BLOCKQUOTE>

This is an incorrect implication; however, it is also not dispelled in
14.7.1&nbsp;



 <A HREF="template.html#temp.inst">temp.inst</A>
 paragraph 6:

<BLOCKQUOTE>
If an implicit instantiation of a class template specialization is
required and the template is declared but not defined, the program is
ill-formed.
</BLOCKQUOTE>

This wording says nothing about the translation unit in which the
definition must be provided.  Contrast this with
14.7.2&nbsp;



 <A HREF="template.html#temp.explicit">temp.explicit</A>
 paragraph 3:

<BLOCKQUOTE>
A definition of a class template or a class member template shall be
in scope at the point of the explicit instantiation of the class
template or class member template.
</BLOCKQUOTE>

<P>
<B>Suggested resolution:</B>
</P>

<BR>
<UL>
<LI>Change 14&nbsp;



 <A HREF="template.html#temp">temp</A>
 paragraph 8 to say
that "An exported <B>non-class</B> template need only be declared..."</LI>

<LI>Change 14.7.1&nbsp;



 <A HREF="template.html#temp.inst">temp.inst</A>
 paragraph 6 to
use wording similar to that of
14.7.2&nbsp;



 <A HREF="template.html#temp.explicit">temp.explicit</A>
 paragraph 3 regarding
the requirement for a definition of the class template to be in scope.</LI>
</UL>

<P>(See also <A HREF="
     cwg_active.html#212">issue 212</A>.)</P>

<P>
<B>Notes from 04/00 meeting:</B>
</P>

<P>John Spicer opined that even though 14&nbsp;



 <A HREF="template.html#temp">temp</A>
paragraph 7 speaks of "declaring a class template exported," that does
not mean that the class template is "an exported template" in the
sense of paragraph 8.  He suggested clarifying paragraph 7 to that
effect instead of the change to paragraph 8 suggested above, and
questioned the need for a change to 14.7.1&nbsp;



 <A HREF="template.html#temp.inst">temp.inst</A>.</P>

<P>
<B>Notes from the 4/02 meeting:</B>
</P>

<P>This is resolved by the proposed changes for
<A HREF="
     cwg_defects.html#323">issue 323</A>.</P>

<BR>
<BR>
<HR>
<A NAME="323"></A>
<H4>323.
  
Where must <TT>export</TT> appear?
</H4>
<B>Section: </B>14&nbsp;



 <A HREF="template.html#temp">temp</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Daveed Vandevoorde
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>14 Nov 2001<BR>


<P>[Voted into WP at April 2003 meeting.]</P>



<P>The standard doesn't seem to describe whether the keyword <TT>export</TT>
should appear on exported template declarations that are not used or
defined in that particular translation unit.</P>

<P>For example:</P>
<PRE>
  // File 1:
  template&lt;typename T&gt; void f();  // export omitted

  // File 2:
  export template&lt;typename T&gt; void f() {}

  int main() { f&lt;int&gt;(); }
</PRE>
<P>Another example is:</P>
<PRE>
  // File 1:
  struct S {
     template&lt;typename T&gt; void m();
  };

  // File 2:
  struct S {
     template&lt;typename T&gt; void m();
  };

  export template&lt;typename T&gt; void S::m() {}

  int main() {
     S s;
     S.m&lt;int&gt;();
  }
</PRE>

<P>I think both examples should be clarified to be invalid.  If a template is 
exported in one translation unit, it should be declared export in all 
translation units in which it appears.</P>

<P>With the current wording, it seems that even the following is valid:</P>
<PRE>
  // File 1:
  export template&lt;typename T&gt; void f();  // export effectively ignored

  // File 2:
  template&lt;typename T&gt; void f() {}  // Inclusion model
  void g() { f&lt;int&gt;(); }

  // File 3:
  void g();
  template&lt;typename T&gt; void f() {}  // Inclusion model

  int main() {
     g();
     f&lt;int&gt;();
  }
</PRE>
 
<P>In fact, I think the declaration in "File 1" could be a definition and this
would still satisfy the the requirements of the standard, which definitely
seems wrong.</P>

<P>
<B>Proposed Resolution (revised October 2002):</B>
</P>

<P>Replace 14&nbsp;



 <A HREF="template.html#temp">temp</A> paragraphs 6, 7, and 8 by the
following text:</P>
<BLOCKQUOTE>
<P>
A <I>template-declaration</I> may be preceded by the <TT>export</TT> keyword.
Such a template is said to be <I>exported</I>.
Declaring exported a class template is equivalent to declaring
exported all of its non-inline member functions, static data members, 
member classes, member class templates, and non-inline member function 
templates.</P>
<P> If a template is exported in one translation unit, it
shall be exported in all translation units in which
it appears; no diagnostic is required.
A declaration of an exported template shall appear with the <TT>export</TT>
keyword before any point of instantiation (14.6.4.1&nbsp;



 <A HREF="template.html#temp.point">temp.point</A>)
of that template in that translation unit.  In addition, the first
declaration of an exported template containing the <TT>export</TT> keyword
must not follow the definition of that template.  The <TT>export</TT>
keyword shall not be used in a friend declaration.</P>
<P> Templates defined in an unnamed namespace, inline functions, and
inline function templates shall not be exported.
An exported non-class template shall be defined only once in a program;
no diagnostic is required. An exported non-class template
need only be declared (and not necessarily defined) in a translation
unit in which it is instantiated.</P>
<P>A non-exported non-class template must be defined in every translation unit
in which it is implicitly instantiated (14.7.1&nbsp;



 <A HREF="template.html#temp.inst">temp.inst</A>),
unless the corresponding
specialization is explicitly instantiated (14.7.2&nbsp;



 <A HREF="template.html#temp.explicit">temp.explicit</A>)
in some translation unit; no diagnostic is required.</P>
</BLOCKQUOTE>

<P> Note: This change also resolves issues <A HREF="
     cwg_defects.html#204">204</A>
and <A HREF="
     cwg_defects.html#335">335</A>.</P>

<BR>
<BR>
<HR>
<A NAME="335"></A>
<H4>335.
  
Allowing <TT>export</TT> on template members of nontemplate classes
</H4>
<B>Section: </B>14&nbsp;



 <A HREF="template.html#temp">temp</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>John Spicer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>30 Jan 2002<BR>


<P>[Voted into WP at April 2003 meeting.]</P>



<P>The syntax for "export" permits it only on template declarations.
Clause 14&nbsp;



 <A HREF="template.html#temp">temp</A> paragraph 6 further restricts "export"
to appear only
on namespace scope declarations.  This means that you can't export
a member template of a non-template class, as in:
<PRE>
  class A {
    template &lt;class T&gt; void f(T);
  };
</PRE>
You can, of course, put export on the definition:
<PRE>
  export template &lt;class T&gt; void A&lt;T&gt;::f(T){}
</PRE>
but in order for the template to be used from other translation units
(the whole point of export) the declaration in the other translation
unit must also be declared export.</P>

<P>There is also the issue of whether or not we should permit this usage:
<PRE>
  export struct A {
    template &lt;class T&gt; void f(T);
  };
</PRE>
My initial reaction is to retain this prohibition as all current uses
of "export" are preceding the "template" keyword.</P>

<P>If we eliminate the requirement that "export" precede "template" there
is a similar issue regarding this case, which is currently prohibited:
<PRE>
  template &lt;class T&gt; struct B {
    export void f();
  };
</PRE>
My preference is still to permit only "export template".</P>

<P>
<B>Notes from the 4/02 meeting:</B>
</P>

<P>This is resolved by the proposed changes for
<A HREF="
     cwg_defects.html#323">issue 323</A>.</P>

<BR>
<BR>
<HR>
<A NAME="184"></A>
<H4>184.
  
Default arguments in template <I>template-parameter</I>s
</H4>
<B>Section: </B>14.1&nbsp;



 <A HREF="template.html#temp.param">temp.param</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>John Spicer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>11 Nov 1999<BR>



<P>[Voted into WP at April 2003 meeting.]</P>



<P>
<U>John Spicer</U>:
Where can default values for the template parameters of
template template parameters be specified and where so they apply?</P>

<P>For normal template parameters, defaults can be specified only in
class template declarations and definitions, and they accumulate
across multiple declarations in the same way that function default
arguments do.</P>

<P>I think that defaults for parameters of template template parameters should
be handled differently, though.  I see no reason why such a default should
extend beyond the template declaration with which it is associated.
In other words, such defaults are a property of a specific template
declaration and are not part of the interface of the template.</P>

<PRE>
    template &lt;class T = float&gt; struct B {};

    template &lt;template &lt;class _T = float&gt; class T&gt; struct A {
        inline void f();
        inline void g();
    };

    template &lt;template &lt;class _T&gt; class T&gt; void A&lt;T&gt;::f() {
        T&lt;&gt; t;  // Okay? (proposed answer - no)
    }

    template &lt;template &lt;class _T = char&gt; class T&gt; // Okay? (proposed answer - yes)
    void A&lt;T&gt;::g() {
        T&lt;&gt; t;  // T&lt;char&gt; or T&lt;float&gt;?  (proposed answer - T&lt;char&gt;)
    }

    int main() {
        A&lt;B&gt; ab;
        ab.f();
    }
</PRE>

<P>I don't think this is clear in the standard.</P>

<P>
<U>Gabriel Dos Reis</U>:
On the other hand I fail to see the reasons why we should introduce
yet another special rule to handle that situation differently.  I
think we should try to keep rules as uniform as possible.
For default values, it has been the case that one
should look for any declaration specifying default values.  Breaking
that rules doesn't buy us anything, at least as far as I can see.
My feeling is that [allowing different defaults in different
declarations] is very confusing.</P>

<P>
<U>Mike Miller</U>:
I'm with John on this one.  Although we don't have the
concept of "prototype scope" for template parameter lists,
the analogy with function parameters would suggest that the
two declarations of <TT>T</TT> (in the template class definition and
the template member function definition) are separate
declarations and completely unrelated.  While it's true that
you accumulate default arguments on top-level declarations in
the same scope, it seems to me a far leap to say that we ought
also to accumulate default arguments in nested declarations.
I would expect those to be treated as being in different
scopes and thus <B>not</B> to share default argument information.</P>

<P>When you look up the name <TT>T</TT> in the definition of
<TT>A&lt;T&gt;::f()</TT>,
the declaration you find has no default argument for the
parameter of <TT>T</TT>, so <TT>T&lt;&gt;</TT> should not be allowed.</P>

<P>
<B>Proposed Resolution (revised October 2002):</B>
</P>

<P>
In 14.1&nbsp;



 <A HREF="template.html#temp.param">temp.param</A>, add the following as a new paragraph
at the end of this section:</P>

<BLOCKQUOTE>
A <I>template-parameter</I> of a template <I>template-parameter</I>
is permitted to have a default <I>template-argument</I>.  When such
default arguments are specified, they apply to the template
<I>template-parameter</I> in the scope of the template
<I>template-parameter</I>.  [<I>Example:</I>
<PRE>
    template &lt;class T = float&gt; struct B {};

    template &lt;template &lt;class TT = float&gt; class T&gt; struct A {
        inline void f();
        inline void g();
    };

    template &lt;template &lt;class TT&gt; class T&gt; void A&lt;T&gt;::f() {
        T&lt;&gt; t;  // error - TT has no default template argument
    }

    template &lt;template &lt;class TT = char&gt; class T&gt;void A&lt;T&gt;::g() {
        T&lt;&gt; t;  // OK - T&lt;char&gt;
    }
</PRE>
<I>-- end example</I>]
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="226"></A>
<H4>226.
  
Default template arguments for function templates
</H4>
<B>Section: </B>14.1&nbsp;



 <A HREF="template.html#temp.param">temp.param</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Bjarne Stroustrup
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>19 Apr 2000<BR>


<P>[Voted into WP at April 2003 meeting.]</P>

<P>The prohibition of default template arguments for function
templates is a misbegotten remnant of the time where freestanding
functions were treated as second class citizens and required all 
template arguments to be deduced from the function arguments
rather than specified.
</P>

<P>The restriction seriously cramps programming style by unnecessarily making 
freestanding functions different from member functions, thus making it harder 
to write STL-style code.</P>

<P>
<B>Suggested resolution:</B>
</P>

<P>Replace</P>

<BLOCKQUOTE>

A default <I>template-argument</I> shall not be specified in a
function template declaration or a function template definition, nor
in the <I>template-parameter-list</I> of the definition of a member of
a class template.

</BLOCKQUOTE>

<P>by</P>

<BLOCKQUOTE>

A default <I>template-argument</I> shall not be specified in the
<I>template-parameter-list</I> of the definition of a member of a
class template.

</BLOCKQUOTE>

<P>The actual rules are as stated for arguments to class templates.
</P>

<P>
<B>Notes from 10/00 meeting:</B>
</P>

<P>The core language working group was amenable to this change.
Questions arose, however, over the interaction between default
template arguments and template argument deduction: should it be
allowed or forbidden to specify a default argument for a deduced
parameter?  If it is allowed, what is the meaning: should one or
the other have priority, or is it an error if the default and
deduced arguments are different?</P>

<P>
<B>Notes from the 10/01 meeting:</B>
</P>

<P>It was decided that default arguments should be allowed on friend
declarations only when the declaration is a definition.  It was
also noted that it is not necessary to insist that if there
is a default argument for a given parameter all following parameters
have default arguments, because (unlike in the class case)
arguments can be deduced if they are not specified.</P>

<P>Note that there is an interaction with
<A HREF="
     cwg_defects.html#115">issue 115</A>.</P>

<P>
<B>Proposed resolution (revised October 2002):</B>
</P>

<OL>
<LI>
<P>In 14.1&nbsp;



 <A HREF="template.html#temp.param">temp.param</A> paragraph 9, replace</P>

<BLOCKQUOTE>
A default <I>template-argument</I> may be specified in a class
template declaration or a class template definition.  A default
<I>template-argument</I> shall not be specified in a function
template declaration or a function template definition, nor in the
<I>template-parameter-list</I> of the definition of a member of a
class template.
</BLOCKQUOTE>

<P>with</P>

<BLOCKQUOTE>
A default <I>template-argument</I> may be specified in a template
declaration.  A default
<I>template-argument</I> shall not be specified in the
<I>template-parameter-list</I>s of the definition of a member
of a class template that appears outside of the member's class.
</BLOCKQUOTE>

</LI>

<LI>
<P>In 14.1&nbsp;



 <A HREF="template.html#temp.param">temp.param</A> paragraph 9, replace</P>

<BLOCKQUOTE>
A default <I>template-argument</I> shall not be specified in a friend template
declaration.
</BLOCKQUOTE>

<P>with</P>

<BLOCKQUOTE>
A default <I>template-argument</I> shall not be specified in a friend
class template declaration.  If a friend function template declaration
specifies a default <I>template-argument</I>, that declaration shall be
a definition and shall be the only declaration of the function template
in the translation unit.
</BLOCKQUOTE>

</LI>

<LI>
<P>In 14.1&nbsp;



 <A HREF="template.html#temp.param">temp.param</A> paragraph 11, replace</P>

<BLOCKQUOTE>
If a <I>template-parameter</I> has a default <I>template-argument</I>,
all subsequent <I>template-parameters</I> shall have a default
<I>template-argument</I> supplied.
</BLOCKQUOTE>

<P>with</P>

<BLOCKQUOTE>
If a <I>template-parameter</I> of a class template has a default
<I>template-argument</I>, all subsequent <I>template-parameters</I>
shall have a default <I>template-argument</I> supplied.
[<I>Note:</I> This is not a requirement for function templates
because template arguments might be deduced (14.8.2&nbsp;



 <A HREF="template.html#temp.deduct">temp.deduct</A>).]
</BLOCKQUOTE>
</LI>

<LI>
<P>In 14.8&nbsp;



 <A HREF="template.html#temp.fct.spec">temp.fct.spec</A> paragraph 1, replace</P>

<BLOCKQUOTE>
Template arguments can either be explicitly specified when
naming the function template specialization or be deduced
(14.8.2&nbsp;



 <A HREF="template.html#temp.deduct">temp.deduct</A>) from the context, e.g. from the
function arguments in a call to the function template
specialization.
</BLOCKQUOTE>

<P>with</P>

<BLOCKQUOTE>
Template arguments can be explicitly specified when naming the
function template specialization, deduced from the context
(14.8.2&nbsp;



 <A HREF="template.html#temp.deduct">temp.deduct</A>), e.g., deduced from the function
arguments in a call to the function template specialization), or
obtained from default template arguments.
</BLOCKQUOTE>

</LI>

<LI>
<P>In 14.8.1&nbsp;



 <A HREF="template.html#temp.arg.explicit">temp.arg.explicit</A> paragraph 2, replace</P>

<BLOCKQUOTE>
Trailing template arguments that can be deduced
(14.8.2&nbsp;



 <A HREF="template.html#temp.deduct">temp.deduct</A>) may be omitted from the list
of explicit <I>template-argument</I>s.
</BLOCKQUOTE>

<P>with</P>

<BLOCKQUOTE>
Trailing template arguments that can be deduced
(14.8.2&nbsp;



 <A HREF="template.html#temp.deduct">temp.deduct</A>) or obtained from default
<I>template-argument</I>s may be omitted from the list of
explicit <I>template-argument</I>s.
</BLOCKQUOTE>

</LI>

<LI>
<P>In 14.8.2&nbsp;



 <A HREF="template.html#temp.deduct">temp.deduct</A> paragraph 1, replace</P>

<BLOCKQUOTE>
The values can be either explicitly specified or, in some
cases, deduced from the use.
</BLOCKQUOTE>

<P>with</P>

<BLOCKQUOTE>
The values can be explicitly specified or, in some cases,
be deduced from the use or obtained from default
<I>template-argument</I>s.
</BLOCKQUOTE>

</LI>

<LI>
<P>In 14.8.2&nbsp;



 <A HREF="template.html#temp.deduct">temp.deduct</A> paragraph 4, replace</P>

<BLOCKQUOTE>
The resulting substituted and adjusted function type is used as
the type of the function template for template argument
deduction.  When all template arguments have been deduced, all
uses of template parameters in nondeduced contexts are replaced
with the corresponding deduced argument values.  If the
substitution results in an invalid type, as described above,
type deduction fails.
</BLOCKQUOTE>

<P>with</P>

<BLOCKQUOTE>
<P>The resulting substituted and adjusted function type is used as
the type of the function template for template argument
deduction.  If a template argument has not been deduced, its
default template argument, if any, is used.  [<I>Example:</I>
</P>

<PRE>
    template &lt;class T, class U = double&gt;
    void f(T t = 0, U u = 0);

    void g()
    {
        f(1, 'c');         // f&lt;int,char&gt;(1,'c')
        f(1)               // f&lt;int,double&gt;(1,0)
        f();               // error: T cannot be deduced
        f&lt;int&gt;();          // f&lt;int,double&gt;(0,0)
        f&lt;int,char&gt;();     // f&lt;int,char&gt;(0,0)
    }
</PRE>

<P>---<I>end example</I>]</P>

<P>When all template arguments have been deduced or obtained from
default template arguments, all uses of template parameters in
nondeduced contexts are replaced with the corresponding deduced
or default argument values.  If the substitution results in an
invalid type, as described above, type deduction fails.</P>
</BLOCKQUOTE>
</LI>
</OL>

<BR>
<BR>
<HR>
<A NAME="401"></A>
<H4>401.
  
When is access for template parameter default arguments checked?
</H4>
<B>Section: </B>14.1&nbsp;



 <A HREF="template.html#temp.param">temp.param</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Adamczyk
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>27 Jan 2003<BR>


<P>[Voted into WP at October 2005 meeting.]</P>

<P>Is the following well-formed?</P>
<PRE>
  class policy {};
  class policy_interface {};
  template &lt;class POLICY_INTERFACE&gt;
  class aph {
  protected:
    typedef POLICY_INTERFACE PI;
  };
  template &lt;class POLICY, class BASE, class PI = typename BASE::PI&gt;
  class ConcretePolicyHolder : public BASE, protected POLICY
  {};
  ConcretePolicyHolder &lt; policy , aph &lt; policy_interface &gt; &gt; foo;
  void xx() { }
</PRE>
<P>The issue is whether the access to the default argument type BASE::PI
is checked before or after it is known that BASE is a base class of
the template. To some extent, one needs to develop the list of
template arguments (and therefore evaluate the default argument)
before one can instantiate the template, and
one does not know what base classes the template has until it has
been instantiated.</P>

<P>
<B>Notes from April 2003 meeting:</B>
</P>

<P>Shortened example:</P>
<PRE>
  class B {
  protected:
    typedef int A;
  };
  template&lt;class T, class U = typename T::A&gt;
  class X : public T
  { };
</PRE>

<P>The convincing argument here is that if we had only the declaration
of the template (including the default argument), we would expect
it to be usable in exactly the same way as the version with the
definition.  However, the special access needed is visible only
when the definition is available.  So the above should be an error,
and information from the definition cannot affect the access of
the default arguments.</P>

<P>
<B>Proposed Resolution (April 2003):</B>
</P>

<P> Add a new paragraph 16 to 14.1&nbsp;



 <A HREF="template.html#temp.param">temp.param</A> after
paragraph 15:</P>
<BLOCKQUOTE>
Since a default <I>template-argument</I> is encountered before any
<I>base-clause</I> there is no special access to members used in a default
<I>template-argument</I>.  <I>[Example:</I>
<PRE>
  class B {};
  template &lt;class T&gt; class C {
  protected:
     typedef T TT;
  };

  template &lt;class U, class V = typename U::TT&gt;
  class D : public U {};

  D &lt;C&lt;B&gt; &gt; d;  // access error, C::TT is protected
</PRE>
<I>--- end example]</I>
</BLOCKQUOTE>

<P>
<B>Notes from October 2003 meeting:</B>
</P>

<P>We decided that template parameter default arguments should
have their access checked in the context where they appear
without special access for the entity declared (i.e., they are
different than normal function default arguments).  One reason:
we don't know the instance of the template when we need the
value.  Second reason: compilers want to parse and throw away the
form of the template parameter default argument, not save it and
check it for each instantiation.</P>

<P>Class templates should be treated the same as function templates
in this regard.  The base class information is in the same category
as friend declarations inside the class itself -- not available.
If the body were used one would need to instantiate it in order
to know whether one can name it.</P>

<P>
<B>Proposed resolution (October, 2004):</B>
</P>

<P>Add the following as a new paragraph following the last
paragraph of 11&nbsp;



 <A HREF="access.html#class.access">class.access</A> (but before the new
paragraph inserted by the resolution of <A HREF="
     cwg_defects.html#372">issue 372</A>, if adopted):</P>

<BLOCKQUOTE>

<P>The names in a default <I>template-argument</I> (14.1&nbsp;



 <A HREF="template.html#temp.param">temp.param</A>) have their access checked in the context in which
they appear rather than at any points of use of the default
<I>template-argument</I>. [<I>Example:</I>
</P>

<PRE>
    class B {};
    template &lt;class T&gt; class C {
    protected:
       typedef T TT;
    };

    template &lt;class U, class V = typename U::TT&gt;
    class D : public U {};

    D &lt;C&lt;B&gt; &gt;* d;  // access error, C::TT is protected
</PRE>

<P>&mdash;<I>end example</I>]</P>
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="228"></A>
<H4>228.
  
Use of <TT>template</TT> keyword with non-member templates
</H4>
<B>Section: </B>14.2&nbsp;



 <A HREF="template.html#temp.names">temp.names</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Daveed Vandevoorde
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>4 May 2000<BR>


<P>[Voted into WP at April 2003 meeting.]</P>



<P>Consider the following example:</P>

<PRE>
    template&lt;class T&gt;
    struct X {
       virtual void f();
    };

    template&lt;class T&gt;
    struct Y {
       void g(X&lt;T&gt; *p) {
	  p-&gt;template X&lt;T&gt;::f();
       }
    };
</PRE>

<P>This is an error because <TT>X</TT> is not a member template;
14.2&nbsp;



 <A HREF="template.html#temp.names">temp.names</A> paragraph 5 says:</P>

<BLOCKQUOTE>
If a name prefixed by the keyword <TT>template</TT> is not the name 
of a member template, the program is ill-formed.
</BLOCKQUOTE>

<P>In a way this makes perfect sense: <TT>X</TT> is found to be a template
using ordinary lookup even though <TT>p</TT> has a dependent type.
However, I think this makes the use of the <TT>template</TT> prefix
even harder to teach.</P>

<P>Was this intentionally outlawed?</P>

<P>
<B>Proposed Resolution (4/02):</B>
</P>

<P>Elide the first use of the word "member" in
14.2&nbsp;



 <A HREF="template.html#temp.names">temp.names</A> paragraph 5 so that its first sentence reads:</P>
<BLOCKQUOTE>
If a name prefixed by the keyword <TT>template</TT> is not the name of a
<S>member</S> template, the program is ill-formed.
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="246"></A>
<H4>246.
  
Jumps in <I>function-try-block</I> handlers
</H4>
<B>Section: </B>14.3&nbsp;



 <A HREF="template.html#temp.arg">temp.arg</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>15 Sep 2000<BR>


<P>[Moved to DR at 4/01 meeting.]</P>



<P>Is it permitted to jump from a handler of a
<I>function-try-block</I> into the body of the function?</P>

<P>15&nbsp;



 <A HREF="except.html#except">except</A> paragraph 2 would appear to disallow
such a jump:</P>

<BLOCKQUOTE>

A <TT>goto</TT>, <TT>break</TT>, <TT>return</TT>, or <TT>continue</TT>
statement can be used to transfer control out of a try block or
handler, but not into one.

</BLOCKQUOTE>

<P>However, 15.3&nbsp;



 <A HREF="except.html#except.handle">except.handle</A> paragraph 14 mentions
only constructors and destructors for the prohibition:</P>

<BLOCKQUOTE>

If the handlers of a <I>function-try-block</I> contain a jump into the
body of a constructor or destructor, the program is ill-formed.

</BLOCKQUOTE>

<P>Is this paragraph simply reemphasizing the more general
restriction, or does it assume that such a jump would be permitted
for functions other than constructors or destructors?  If the
former interpretation is correct, it is confusing and should be
either eliminated or turned into a note.  If the latter
interpretation is accurate, 15&nbsp;



 <A HREF="except.html#except">except</A> paragraph 2
must be revised.</P>

<P>(See also <A HREF="
     cwg_defects.html#98">issue 98</A>.)</P>

<P>
<B>Proposed resolution (04/01):</B>
</P>

<P>Delete 15.3&nbsp;



 <A HREF="except.html#except.handle">except.handle</A> paragraph 14.</P>

<BR>
<BR>
<HR>
<A NAME="62"></A>
<H4>62.
  
Unnamed members of classes used as type parameters
</H4>
<B>Section: </B>14.3.1&nbsp;



 <A HREF="template.html#temp.arg.type">temp.arg.type</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Adamczyk
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>13 Oct 1998<BR>



<P>[Moved to DR at 4/01 meeting.]</P>

<P>Section 14.3.1&nbsp;



 <A HREF="template.html#temp.arg.type">temp.arg.type</A>
 paragraph 2 says</P>
<BLOCKQUOTE>A local type, a type with no linkage, an unnamed type or a
type compounded from any of these types shall not be used as a <I>template-argument
</I>for a template <I>type-parameter</I>.</BLOCKQUOTE>
<P>It probably wasn't intended that classes with unnamed members should be
included in this list, but they are arguably compounded from unnamed types.</P>

<P>
<B>Proposed resolution (04/01):</B>
</P>

<P>In 14.3.1&nbsp;



 <A HREF="template.html#temp.arg.type">temp.arg.type</A> paragraph 2, change</P>

<BLOCKQUOTE>

A local type, a type with no linkage, an unnamed type or a type
compounded from any of these types shall not be used as a
<I>template-argument</I> for a template <I>type-parameter</I>.

</BLOCKQUOTE>

<P>to</P>

<BLOCKQUOTE>

The following types shall not be used as a <I>template-argument</I>
for a template <I>type-parameter</I>:

<UL>

<LI>a type whose name has no linkage</LI>

<LI>an unnamed class or enumeration type that has no name for
linkage purposes (7.1.3&nbsp;



 <A HREF="dcl.html#dcl.typedef">dcl.typedef</A>)</LI>

<LI>a cv-qualified version of one of the types in this list</LI>

<LI>a type created by application of declarator operators to one
of the types in this list</LI>

<LI>a function type that uses one of the types in this list</LI>

</UL>

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="354"></A>
<H4>354.
  
Null as nontype template argument
</H4>
<B>Section: </B>14.3.2&nbsp;



 <A HREF="template.html#temp.arg.nontype">temp.arg.nontype</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>John Spicer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>2 May 2002<BR>


<P>[Voted into WP at October 2005 meeting.]</P>



<P>The standard does not permit a null value to be used as a nontype template
argument for a nontype template parameter that is a pointer.</P>

<P>This code is accepted by EDG, Microsoft, Borland and Cfront, but rejected
by g++ and Sun:</P>
<PRE>
  template &lt;int *p&gt; struct A {};
  A&lt;(int*)0&gt; ai;
</PRE>
<P>I'm not sure this was ever explicitly considered by the committee.
Is there any reason to permit this kind of usage?</P>

<P>
<U>Jason Merrill</U>:
I suppose it might be useful for a program to be able to express a
degenerate case using a null template argument.  I think allowing it would
be harmless.</P>

<P>
<B>Notes from October 2004 meeting:</B>
</P>

<P>CWG decided that it would be desirable to allow null pointers
as nontype template arguments, even though they are not
representable in some current ABIs.  There was some discussion
over whether to allow a bare <TT>0</TT> to be used with a pointer
nontype template parameter.  The following case was decisive:</P>

<PRE>
    template&lt;int i&gt; void foo();
    template&lt;int* i&gt; void foo();
    ...
    foo&lt;0&gt;();
</PRE>

<P>The current wording of 14.3&nbsp;



 <A HREF="template.html#temp.arg">temp.arg</A> paragraph 7
disambiguates the function call in favor of the <TT>int</TT>
version.  If the null pointer conversion were allowed for pointer
nontype template parameters, this case would become ambiguous, so
it was decided to require a cast.</P>

<P>
<B>Proposed resolution (April, 2005):</B>
</P>

<OL>

<LI>
<P>In 14.3.2&nbsp;



 <A HREF="template.html#temp.arg.nontype">temp.arg.nontype</A> paragraph 1, insert the
following after the third bullet:</P>

<UL>

<LI>
<P>a constant expression that evaluates to a null pointer
value (4.10&nbsp;



 <A HREF="conv.html#conv.ptr">conv.ptr</A>); or</P>
</LI>

<LI>
<P>a constant expression that evaluates to a null member
pointer value (4.11&nbsp;



 <A HREF="conv.html#conv.mem">conv.mem</A>); or</P>
</LI>

</UL>

</LI>

<LI>
<P>Add the indicated text to the note in the second bullet of
14.3.2&nbsp;



 <A HREF="template.html#temp.arg.nontype">temp.arg.nontype</A> paragraph 5:</P>

<BLOCKQUOTE>

[<I>Note:</I> In particular, neither the null pointer conversion
(4.10&nbsp;



 <A HREF="conv.html#conv.ptr">conv.ptr</A>) nor the derived-to-base conversion
(4.10&nbsp;



 <A HREF="conv.html#conv.ptr">conv.ptr</A>) are applied. Although <TT>0</TT> is a valid
<I>template-argument</I> for a non-type <I>template-parameter</I> of integral
type, it is not a valid <I>template-argument</I> for a non-type
<I>template-parameter</I> of pointer type. <B>However, <TT>(int*)0</TT> is a valid
<I>template-argument</I> for a non-type <I>template-parameter</I> of type
&ldquo;pointer to int.&rdquo;</B> &mdash;<I>end note</I>]

</BLOCKQUOTE>

</LI>

<LI>
<P>Replace the normative wording of 14.4&nbsp;



 <A HREF="template.html#temp.type">temp.type</A> paragraph 1 with the following:</P>

<BLOCKQUOTE>

<P>Two <I>template-id</I>s refer to the same class or function
if</P>

<UL>

<LI>their <I>template-name</I>s refer to the same template, and</LI>

<LI>their corresponding type <I>template-argument</I>s are the
same type, and</LI>

<LI>their corresponding non-type <I>template-argument</I>s of
integral or enumeration type have identical values, and</LI>

<LI>their corresponding non-type <I>template-argument</I>s of
pointer type refer to the same external object or function or are
both the null pointer value, and</LI>

<LI>their corresponding non-type <I>template-argument</I>s of
pointer-to-member type refer to the same class member or are both
the null member pointer value, and</LI>

<LI>their corresponding non-type <I>template-arguments</I>s for
template parameters of reference type refer to the same external
object or function, and</LI>

<LI>their corresponding template <I>template-argument</I>s refer
to the same template.</LI>

</UL>

</BLOCKQUOTE>

</LI>
</OL>

<BR>
<BR>
<HR>
<A NAME="329"></A>
<H4>329.
  
Evaluation of friends of templates
</H4>
<B>Section: </B>14.5.3&nbsp;



 <A HREF="template.html#temp.friend">temp.friend</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>John Spicer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>19 Dec 2001<BR>


<P>[Voted into WP at October 2003 meeting.]</P>

<P>14.5.3&nbsp;



 <A HREF="template.html#temp.friend">temp.friend</A> paragraph 5 says:</P>
<BLOCKQUOTE>
When a function is defined in a friend function declaration in a class
template, the function is defined at each instantiation of  the  class
template.  The function is defined even if it is never used.  The same
restrictions on multiple declarations and definitions which  apply  to
non-template function declarations and definitions also apply to these
implicit definitions.  [Note: if the function definition is ill-formed
for  a  given specialization of the enclosing class template, the program
is ill-formed even if the function is never used.  ]
</BLOCKQUOTE>

<P>This means that the following program is invalid, even without the call
of <TT>f(ai)</TT>:</P>
<PRE>
  template &lt;class T&gt; struct A {
    friend void f(A a) {
      g(a);
    }
  };
  int main()
  {
    A&lt;int&gt; ai;
  // f(ai);  // Error if f(ai) is actually called
  }
</PRE>
<P>The EDG front end issues an error on this case even if <TT>f(ai)</TT>
is never
called.  Of the compilers I tried (g++, Sun, Microsoft, Borland) we
are the only ones to issue such an error.</P>

<P>This issue came up because there is a library that either deliberately or
accidentally makes use of friend functions that are not valid for certain
instantiations.</P>

<P>The wording in the standard is the result of a deliberate decision made
long ago, but given the fact that most implementations do otherwise it
raises the issue of whether we did the right thing.</P>

<P>Upon further investigation, the current rule was adopted as the resolution
to issue 6.47 in my series of template issue papers.  At the time the
issue was discussed (7/96) most compilers did evaluate such friends.
So it seems that a number of compilers have changed their behavior
since then.</P>

<P>Based on current practice, I think the standard should be changed to
evaluate such friends only when used.</P>

<P>
<B>Proposed resolution (October 2002):</B>
</P>

<P>Change section 14.5.3&nbsp;



 <A HREF="template.html#temp.friend">temp.friend</A>
paragraph 5 from:
<BLOCKQUOTE>
When a function is defined
in a friend function declaration in a class template,
the function is defined at each instantiation of the class template.
The function is defined even if it is never used.
The same restrictions on multiple declarations and definitions
which apply to non-template function declarations and definitions
also apply to these implicit definitions.
[<I>Note:</I>
if the function definition is ill-formed for a given specialization of the
enclosing class template, the program is ill-formed even if the function
is never used.
]
</BLOCKQUOTE>
to:
<BLOCKQUOTE>
When a function is defined 
in a friend function declaration in a class template,
the function is instantiated when the function is used.
The same restrictions on multiple declarations and definitions
that apply to non-template function declarations and definitions
also apply to these implicit definitions.
</BLOCKQUOTE>
Note the change from "which" to "that" in the last sentence.
</P>

<BR>
<BR>
<HR>
<A NAME="410"></A>
<H4>410.
  
Paragraph missed in changes for issue 166
</H4>
<B>Section: </B>14.5.3&nbsp;



 <A HREF="template.html#temp.friend">temp.friend</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>John Spicer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>18 Apr 2003<BR>


<P>[Voted into WP at October 2004 meeting.]</P>

<P>14.5.3&nbsp;



 <A HREF="template.html#temp.friend">temp.friend</A> paragraph 2 was overlooked when the
changes for <A HREF="
     cwg_defects.html#166">issue 166</A> were made.</P>

<P>The friend declaration of f&lt;&gt;(int) is now valid.</P>

<BLOCKQUOTE>
A  friend  function declaration that is not a template declaration and
in which the name of the friend is an  unqualified <I>template-id</I>  shall
refer  to  a  specialization  of  a  function template declared in the
nearest enclosing namespace scope.  [<I>Example:</I>
<PRE>
  namespace N {
          template &lt;class T&gt; void f(T);
          void g(int);
          namespace M {
                  template &lt;class T&gt; void h(T);
                  template &lt;class T&gt; void i(T);
                  struct A {
                          friend void f&lt;&gt;(int);   // ill-formed - N::f
                          friend void h&lt;&gt;(int);   // OK - M::h
                          friend void g(int);     // OK - new decl of M::g
                          template &lt;class T&gt; void i(T);
                          friend void i&lt;&gt;(int);   // ill-formed - A::i
                  };
          }
  }
</PRE>
<I>--end example</I>]
</BLOCKQUOTE>

<P>
<B>Proposed Resolution (October 2003):</B>
</P>

<P> Remove 14.5.3&nbsp;



 <A HREF="template.html#temp.friend">temp.friend</A> paragraph 2:</P>

<BLOCKQUOTE>
A  friend  function declaration that is not a template declaration and
in which the name of the friend is an  unqualified <I>template-id</I>  shall
refer  to  a  specialization  of  a  function template declared in the
nearest enclosing namespace scope.  [<I>Example:</I>
<PRE>
  namespace N {
          template &lt;class T&gt; void f(T);
          void g(int);
          namespace M {
                  template &lt;class T&gt; void h(T);
                  template &lt;class T&gt; void i(T);
                  struct A {
                          friend void f&lt;&gt;(int);   // ill-formed - N::f
                          friend void h&lt;&gt;(int);   // OK - M::h
                          friend void g(int);     // OK - new decl of M::g
                          template &lt;class T&gt; void i(T);
                          friend void i&lt;&gt;(int);   // ill-formed - A::i
                  };
          }
  }
</PRE>
<I>--end example</I>]
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="286"></A>
<H4>286.
  
Incorrect example in partial specialization
</H4>
<B>Section: </B>14.5.4&nbsp;



 <A HREF="template.html#temp.class.spec">temp.class.spec</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Martin Sebor
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>09 May 2001<BR>


<P>[Moved to DR at 4/02 meeting.]</P>



<P>The example in 14.5.4&nbsp;



 <A HREF="template.html#temp.class.spec">temp.class.spec</A> paragraph 6 is
incorrect.  It reads,</P>

<PRE>
    template&lt;class T&gt; struct A {
        class C {
            template&lt;class T2&gt; struct B { };
        };
    };

    // partial specialization of A&lt;T&gt;::C::B&lt;T2&gt;
    template&lt;class T&gt; template&lt;class T2&gt;
        struct A&lt;T&gt;::C::B&lt;T2*&gt; { };

    A&lt;short&gt;::C::B&lt;int*&gt; absip; // uses partial specialization
</PRE>

<P>Because <TT>C</TT> is a <TT>class</TT> rather than a <TT>struct</TT>,
the use of the name <TT>B</TT> is inaccessible.</P>

<P>
<B>Proposed Resolution (10/01):</B>
</P>

<P>Change <TT>class C</TT> to <TT>struct C</TT> in the example in
14.5.4&nbsp;



 <A HREF="template.html#temp.class.spec">temp.class.spec</A> paragraph 6.  The example becomes</P>
<PRE>
    template&lt;class T&gt; struct A {
        struct C {
            template&lt;class T2&gt; struct B { };
        };
    };

    // partial specialization of A&lt;T&gt;::C::B&lt;T2&gt;
    template&lt;class T&gt; template&lt;class T2&gt;
        struct A&lt;T&gt;::C::B&lt;T2*&gt; { };

    A&lt;short&gt;::C::B&lt;int*&gt; absip; // uses partial specialization
</PRE>

<BR>
<BR>
<HR>
<A NAME="214"></A>
<H4>214.
  
Partial ordering of function templates is underspecified
</H4>
<B>Section: </B>14.5.5.2&nbsp;



 <A HREF="template.html#temp.func.order">temp.func.order</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Martin von Loewis/Martin Sebor
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>13 Mar 2000<BR>


<P>[Voted into WP at October 2003 meeting.]</P>

<P>In 14.5.5.2&nbsp;



 <A HREF="template.html#temp.func.order">temp.func.order</A>, partial ordering is explained in
terms of template argument deduction. However, the exact procedure for
doing so is not specified. A number of details are missing, they are
explained as sub-issues below.</P>

<OL>

<LI>14.5.5.2&nbsp;



 <A HREF="template.html#temp.func.order">temp.func.order</A> paragraph 2 refers to
14.8.2&nbsp;



 <A HREF="template.html#temp.deduct">temp.deduct</A> for argument deduction. This is the
wrong reference; it explains how explicit arguments are processed
(paragraph 2) and how function parameter types are adjusted (paragraph
3). Neither of these steps is meaningful in the context of partial
ordering. Next in deduction follows one of the steps in 14.8.2.1&nbsp;



 <A HREF="template.html#temp.deduct.call">temp.deduct.call</A>, 14.8.2.2&nbsp;



 <A HREF="template.html#temp.deduct.funcaddr">temp.deduct.funcaddr</A>, 14.8.2.3&nbsp;



 <A HREF="template.html#temp.deduct.conv">temp.deduct.conv</A>, or 14.8.2.5&nbsp;



 <A HREF="template.html#temp.deduct.type">temp.deduct.type</A>. The standard
does not specify which of these contexts apply to partial
ordering. </LI>

<LI>Because 14.8.2.1&nbsp;



 <A HREF="template.html#temp.deduct.call">temp.deduct.call</A> and 14.8.2.3&nbsp;



 <A HREF="template.html#temp.deduct.conv">temp.deduct.conv</A> both start with actual function parameters, it is
meaningful to assume that partial ordering uses 14.8.2.5&nbsp;



 <A HREF="template.html#temp.deduct.type">temp.deduct.type</A>, which only requires types. With that assumption,
the example in 14.5.5.2&nbsp;



 <A HREF="template.html#temp.func.order">temp.func.order</A> paragraph 5 becomes
incorrect, considering the two templates

<PRE>
    template&lt;class T&gt; void g(T);  // #1
    template&lt;class T&gt; void g(T&amp;); // #2
</PRE>

Here, #2 is at least as specialized as #1: With a synthetic type
<TT>U</TT>, #2 becomes <TT>g(U&amp;)</TT>; argument deduction against
#1 succeeds with <TT>T=U&amp;</TT>. However, #1 is not at least as
specialized as #2: Deducing <TT>g(U)</TT> against <TT>g(T&amp;)</TT>
fails. Therefore, the second template is more specialized than the
first, and the call <TT>g(x)</TT> is not ambiguous.</LI>

<LI>According to John Spicer, the intent of the partial ordering was
that it uses deduction as in a function call (14.8.2.1&nbsp;



 <A HREF="template.html#temp.deduct.call">temp.deduct.call</A>), which is indicated by the mentioning of "exact
match" in 14.5.5.2&nbsp;



 <A HREF="template.html#temp.func.order">temp.func.order</A> paragraph 4. If that is
indeed the intent, it should be specified how values are obtained for
the step in 14.8.2.1&nbsp;



 <A HREF="template.html#temp.deduct.call">temp.deduct.call</A> paragraph 1, where the
types of the arguments are determined. Also, since 14.8.2.1&nbsp;



 <A HREF="template.html#temp.deduct.call">temp.deduct.call</A> paragraph 2 drops references from the parameter
type, symmetrically, references should be dropped from the argument
type (which is done in 5&nbsp;



 <A HREF="expr.html#expr">expr</A> paragraph 2, for a true
function call).</LI>

<LI>14.5.5.2&nbsp;



 <A HREF="template.html#temp.func.order">temp.func.order</A> paragraph 4 requires an "exact
match" for the "deduced parameter types". It is not clear whether this
refers to the template parameters, or the parameters of the template
function. Considering the example

<PRE>
    template&lt;class S&gt; void g(S);  // #1
    template&lt;class T&gt; void g(T const &amp;); // #3
</PRE>

Here, #3 is clearly at least as specialized as #1. To determine
whether #1 is at least as specialized as #3, a unique type <TT>U</TT>
is synthesized, and deduction of <TT>g&lt;U&gt;(U)</TT> is performed
against #3. Following the rules in 14.8.2.1&nbsp;



 <A HREF="template.html#temp.deduct.call">temp.deduct.call</A>,
deduction succeeds with <TT>T=U</TT>.  Since the template argument is
<TT>U</TT>, and the deduced template parameter is also <TT>U</TT>, we
have an exact match between the template parameters. Even though the
conversion from <TT>U</TT> to <TT>U const &amp;</TT> is an exact
match, it is not clear whether the added qualification should be taken
into account, as it is in other places.</LI>

</OL>

<P>
<A HREF="
     cwg_closed.html#200">Issue 200</A> covers a related issue,
illustrated by the following example:</P>

<PRE>
    template &lt;class T&gt; T f(int);
    template &lt;class T, class U&gt; T f(U);
    void g() {
        f&lt;int&gt;(1);
    }
</PRE>

<P>Even though one template is "obviously" more specialized than the
other, deduction fails in both directions because neither function
parameter list allows template parameter <TT>T</TT> to be deduced.</P>

<P>(See also <A HREF="
     cwg_defects.html#250">issue 250</A>.)</P>



<P>
<U>Nathan Sidwell</U>:</P>

<P>14.5.5.2&nbsp;



 <A HREF="template.html#temp.func.order">temp.func.order</A> describes the partial ordering of function
templates. Paragraph 5 states,
<BLOCKQUOTE>
A template is more specialized than another if, and
only if, it is at least as specialized as the other
template and that template is not at least as
specialized as the first.
</BLOCKQUOTE>
To paraphrase, given two templates A &amp; B, if A's template
parameters can be deduced by B, but B's cannot be deduced by
A, then A is more specialized than B. Deduction is done as
if for a function call. In particular, except for conversion
operators, the return type is not involved in deduction.
This leads to the following templates and use being
unordered. (This example is culled from G++ bug report 4672
http://gcc.gnu.org/cgi-bin/gnatsweb.pl?cmd=view&amp;pr=4672)
<PRE>
  template &lt;typename T, class U&gt; T checked_cast(U from); //#1
  template &lt;typename T, class U&gt; T checked_cast(U * from); //#2
  class C {};

  void foo (int *arg)
  {
    checked_cast &lt;C const *&gt; (arg);
  }
</PRE>
In the call,</P>
<P>#1 can be deduced with T = 'C const *' and U = 'int *'</P>
<P>#2 can be deduced with T = 'C const *' and U = 'int'</P>

<P>It looks like #2 is more specialized that #1, but
14.5.5.2&nbsp;



 <A HREF="template.html#temp.func.order">temp.func.order</A> does not make it so, as neither template can
deduce 'T' from the other template's function parameters.</P>

<P>Possible Resolutions:</P>
<P>There are several possible solutions, however through
experimentation I have discounted two of them.</P>

<P>Option 1:</P>
<P>When deducing function ordering, if the return type of one of
the templates uses a template parameter, then return types
should be used for deduction.  This, unfortunately, makes
existing well formed programs ill formed. For example
<PRE>
  template &lt;class T&gt; class X {};

  template &lt;class T&gt; X&lt;T&gt; Foo (T *);	// #1
  template &lt;class T&gt; int Foo (T const *); // #2

  void Baz (int *p1, int const *p2)
  {
    int j = Foo (p2); //#3
  }
</PRE>
Here, neither #1 nor #2 can deduce the other, as the return
types fail to match. Considering only the function parameters
gives #2 more specialized than #1, and hence makes the call
#3 well formed.</P>

<P>Option 2:</P>
<P>As option 1, but only consider the return type when deducing
the template whose return type involves template parameters.
This has the same flaw as option 1, and that example is
similarly ill formed, as #1's return type 'X&lt;T,0&gt;' fails to
match 'int' so #1 cannot deduce #2. In the converse direction,
return types are not considered, but the function parameters
fail to deduce.</P>

<P>Option 3:</P>
<P>It is observed that the original example is only callable
with a template-id-expr to supply a value for the first,
undeducible, parameter.  If that parameter were deducible it
would also appear within at least one of the function
parameters.  We can alter paragraph 4 of [temp.func.order]
to indicate that it is not necessary to deduce the parameters
which are provided explicitly, when the call has the form
of a template-id-expr.  This is a safe extension as it only
serves to make ill formed programs well formed. It is also
in line with the concept that deduction for function
specialization order should proceed in a similar manner to
function calling, in that explicitly provided parameter
values are taken into consideration.</P>

<P>
<B>Suggested resolution</B>:</P>
<P>Insert after the first sentence of paragraph 4 in
&nbsp;



 <A HREF=".html#"></A>
</P>
<BLOCKQUOTE>
Should any template parameters remain undeduced, and
the function call be of the form of a <I>template-id-expr</I>,
those template parameters provided in the
<I>template-id-expr</I> may be arbitrarily synthesized prior
to determining whether the deduced arguments generate
a valid function type.
</BLOCKQUOTE>

<P>See also <A HREF="
     cwg_closed.html#200">issue 200</A>.</P>

<P>
<B>(April 2002)</B> John Spicer and John Wiegley have written a
paper on this.  See 02-0051/N1393.</P>

<P>
<B>Proposed resolution (October 2002):</B>
</P>

<P>
Change 14.5.5.2&nbsp;



 <A HREF="template.html#temp.func.order">temp.func.order</A> paragraph 2 to read:</P>
<BLOCKQUOTE>
Partial ordering selects which of two function templates is more
specialized than the other by transforming each template in turn
(see next paragraph) and performing template argument deduction
using the function parameter types, or in the case of a conversion
function the return type.  The deduction process determines whether
one of the templates is more specialized than the other.  If so, the
more specialized template is the one chosen by the partial ordering
process.
</BLOCKQUOTE>
<P>
Change 14.5.5.2&nbsp;



 <A HREF="template.html#temp.func.order">temp.func.order</A> paragraph 3 to read:</P>
<BLOCKQUOTE>
To produce the transformed template, for each type, non-type, or template
template parameter synthesize a unique type, value, or class template
respectively and substitute it for each occurrence of that parameter
in the function type of the template.
</BLOCKQUOTE>

<P>
Change 14.5.5.2&nbsp;



 <A HREF="template.html#temp.func.order">temp.func.order</A> paragraph 4 to read
(note: the section reference should refer to the section added to
14.8.2&nbsp;



 <A HREF="template.html#temp.deduct">temp.deduct</A> below):</P>
<BLOCKQUOTE>
Using the transformed function template's function parameter list, or
in the case of a conversion function its transformed return type,
perform type deduction against the function parameter list (or return
type) of the other function.  The mechanism for performing these
deductions is given in 14.8.2.x.
</BLOCKQUOTE>
<P>
Remove the text of 14.5.5.2&nbsp;



 <A HREF="template.html#temp.func.order">temp.func.order</A> paragraph 5 but
retain the example.  The removed text is:</P>
<BLOCKQUOTE>
A template is more specialized than another if, and only if, it is
at least as specialized as the other template and that template is not
at least as specialized as the first.
</BLOCKQUOTE>
<P>
Insert the following section before 14.8.2.5
(Note that this would either be a new 14.8.2.4, or would be given
a number like 14.8.2.3a.  If neither of these is possible from
a troff point of view, this could be made 14.8.2.5.

)</P>
<BLOCKQUOTE>
<P>
<B>Deducing template arguments when determining the partial ordering
of function templates (temp.deduct.partial)</B>
</P>

<P>
Template argument deduction is done by comparing certain types associated with
the two function templates being compared.</P>
<P>
Two sets of types are used to determine the partial ordering.  For each of
the templates involved there is the original function type and the
transformed function type. [<I>Note:</I>
The creation of the transformed type is
described in 14.5.5.2&nbsp;



 <A HREF="template.html#temp.func.order">temp.func.order</A>.]
The deduction process uses the
transformed type as the argument template and the original type of the
other template as the parameter template.  This process is done twice
for each type involved in the partial ordering comparison: once using
the transformed template-1 as the argument template and template-2 as
the parameter template and again using the transformed template-2 as
the argument template and template-1 as the parameter template.</P>
<P>
The types used to determine the ordering depend on the context in which
the partial ordering is 
<UL>
<LI>
In the context of a function call, the function parameter types
are used.</LI>
<LI>
In the context of a call to a conversion operator, the return types of
the conversion function templates are used.</LI>
<LI>
In other contexts (14.5.5.2&nbsp;



 <A HREF="template.html#temp.func.order">temp.func.order</A>),
the function template's function type is used.</LI>
</UL>
</P>

<P>
Each type from the parameter template and the corresponding type from the
argument template are used as the types of <TT>P</TT> and <TT>A</TT>.</P>
<P>
Before the partial ordering is done, certain transformations are performed
on the types used for partial ordering:
<UL>
<LI>
If <TT>P</TT> is a reference type, <TT>P</TT> is replaced by the type
referred to.</LI>
<LI>
If <TT>A</TT> is a reference type, <TT>A</TT> is replaced by the type
referred to.</LI>
</UL>
</P>

<P>
If both <TT>P</TT> and <TT>A</TT> were reference types (before being replaced
with the type referred to above), determine which
of the two types (if any) is more cv-qualified than the other; otherwise
the types are considered to be equally cv-qualified for partial ordering
purposes.  The result of this determination will be used below.</P>

<P>
Remove any top-level cv-qualifiers:
<UL>
<LI>
If <TT>P</TT> is a cv-qualified type, <TT>P</TT> is replaced by the
cv-unqualified version of <TT>P</TT>.</LI>
<LI>
If <TT>A</TT> is a cv-qualified type, <TT>A</TT> is replaced by the
cv-unqualified version of <TT>A</TT>.</LI>
</UL>
</P>

<P>
Using the resulting types <TT>P</TT> and <TT>A</TT> the deduction is then
done as described in (14.8.2.5&nbsp;



 <A HREF="template.html#temp.deduct.type">temp.deduct.type</A>).
If deduction succeeds for a given type,
the type from the argument template is considered to be at least as specialized
as the type from the parameter template.</P>

<P>
If, for a given type, deduction succeeds in both directions (i.e., the
types are identical after the transformations above) if the type from
the argument template is more cv-qualified than the type from the
parameter template (as described above) that type is considered to be
more specialized than the other.  If neither type is more cv-qualified
than the other then neither type is more specialized than the other.</P>

<P>
If for each type being considered a given template is at least as specialized
for all types and more specialized for some set of types and the
other template is not more specialized for any types or is not
at least as specialized for any types, then
the given template is more specialized than the other template.
 Otherwise, neither template
is more specialized than the other.</P>

<P>
In most cases, all template parameters must have values in order for
deduction to succeed, but for partial ordering purposes a template
parameter may remain without a value provided it is not used in the
types being used for partial ordering.  [<I>Note:</I>
A template parameter used
in a non-deduced context is considered used.]</P>

<P>
[<I>Example:</I>
<PRE>
template &lt;class T&gt; T f(int);        // #1
template &lt;class T, class U&gt; T f(U); // #2
void g() {
    f&lt;int&gt;(1);  // Calls #1
}
</PRE>
--<I>end example</I>]
</P>

</BLOCKQUOTE>


<BR>
<BR>
<HR>
<A NAME="180"></A>
<H4>180.
  
<TT>typename</TT> and elaborated types
</H4>
<B>Section: </B>14.6&nbsp;



 <A HREF="template.html#temp.res">temp.res</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>21 Dec 1999<BR>



<P>[Moved to DR at 4/02 meeting.]</P>



<P>
<U>Mike Miller</U>:
A question about <TT>typename</TT> came up in the discussion of
<A HREF="
     cwg_defects.html#68">issue 68</A> that is somewhat relevant
to the idea of omitting
typename in contexts where it is clear that a type is
required: consider something like</P>

<PRE>
        template &lt;class T&gt;
        class X {
            friend class T::nested;
        };
</PRE>

Is <TT>typename</TT> required here?  If so, where would it go?  (The
grammar doesn't seem to allow it anywhere in an
<I>elaborated-type-specifier</I> that has a <I>class-key</I>.)

<P>
<U>Bill Gibbons</U>:
The <TT>class</TT> applies to the last identifier in the qualified name,
since all the previous names must be classes or namespaces.  Since the
name is specified to be a class it does not need <TT>typename</TT>.
[However,] it looks like
14.6&nbsp;



 <A HREF="template.html#temp.res">temp.res</A>
 paragraph 3 requires
<TT>typename</TT> and the following paragraphs
do not exempt this case.  This is not what we agreed on.</P>

<P>
<B>Proposed resolution (04/01):</B>
</P>

<P>In 14.6&nbsp;



 <A HREF="template.html#temp.res">temp.res</A> paragraph 5, change</P>

<BLOCKQUOTE>

The keyword <TT>typename</TT> is not permitted in a
<I>base-specifier</I> or in a <I>mem-initializer</I>; in these
contexts a <I>qualified-name</I> that depends on a
<I>template-parameter</I> (14.6.2&nbsp;



 <A HREF="template.html#temp.dep">temp.dep</A>) is
implicitly assumed to be a type name.

</BLOCKQUOTE>

<P>to</P>

<BLOCKQUOTE>

A qualified name used as the name in a <I>mem-initializer-id</I>,
a <I>base-specifier</I>, or an <I>elaborated-type-specifier</I>
(in the <I>class-key</I> and <TT>enum</TT> forms) is implicitly
assumed to name a type, without the use of the <TT>typename</TT>
keyword.  [<I>Note:</I> the <TT>typename</TT> keyword is not
permitted by the syntax of these constructs.]

</BLOCKQUOTE>

<P>(The expected resolution for <A HREF="
     cwg_defects.html#254">issue 254</A> will remove the <TT>typename</TT> forms from the
grammar for <I>elaborated-type-specifier</I>.  If that
resolution is adopted, the parenthetical phrase "(in the
<I>class-key</I> and <TT>enum</TT> forms)" in the preceding
wording should be removed because those will be the only forms
of <I>elaborated-type-specifier</I>.)</P>

<P>This has been consolidated with the edits for some other
issues.  See N1376=02-0034.</P>

<BR>
<BR>
<HR>
<A NAME="345"></A>
<H4>345.
  
Misleading comment on example in templates chapter
</H4>
<B>Section: </B>14.6&nbsp;



 <A HREF="template.html#temp.res">temp.res</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Jason Shirk
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>18 March 2002<BR>


<P>[Voted into WP at April 2003 meeting.]</P>



<P>The following example from 14.6&nbsp;



 <A HREF="template.html#temp.res">temp.res</A> paragraph 4:</P>
<PRE>
struct A {
	struct X { };
	int X;
};
template&lt;class T&gt; void f(T t) {
	typename T::X x;        //  ill-formed: finds the data member  X
					//  not the member type  X
}
</PRE>

<P>
is not ill-formed.  The intent of the example is obvious, but some
mention should be made that it is only ill-formed when T=A.  For other
T's, it could be well formed.</P>

<P>
<B>Proposed resolution (October 2002):</B>
</P>

<P>
In 14.6&nbsp;



 <A HREF="template.html#temp.res">temp.res</A> paragraph 4, replace the example with:</P>
<BLOCKQUOTE>
<PRE>
struct A {
  struct X { };
  int X; 
} ; 
struct B {
  struct X { };
} ;
template&lt;class T&gt; void f(T t) {
  typename T::X x; 
}
void foo() {
  A a; 
  B b;
  f(b);  // OK -- T::X refers to B::X.
  f(a);  // error: T::X refers to the data member A::X not 
         // the struct A::X.
}
</PRE>
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="382"></A>
<H4>382.
  
Allow <TT>typename</TT> outside of templates
</H4>
<B>Section: </B>14.6&nbsp;



 <A HREF="template.html#temp.res">temp.res</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Adamczyk
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>8 Nov 2002<BR>


<P>[Voted into WP at October 2005 meeting.]</P>

<P>P. J. Plauger, among others, has noted that <TT>typename</TT> is hard
to use, because in a given context it's either required or forbidden,
and it's often hard to tell which.
It would make life easier for programmers if <TT>typename</TT>
could be allowed in places where it is not required, e.g., outside
of templates.</P>

<P>
<B>Notes from the April 2003 meeting:</B>
</P>

<P>There was unanimity on relaxing this requirement on typename.
The question was how much to relax it.  Everyone agreed on allowing
it on all qualified names, which is an easy fix (no syntax change
required).  But should it be allowed other places?  P.J. Plauger
said he'd like to see it allowed anywhere a type name is allowed,
and that it could actually be a decades-late assist for the infamous
"the ice is thin here" typedef problem noted in K&amp;R I.</P>

<P>
<B>Proposed resolution (April 2003):</B>
</P>

<P>Replace the text at the start of 14.6&nbsp;



 <A HREF="template.html#temp.res">temp.res</A> paragraph 3:</P>

<BLOCKQUOTE>
A <I>qualified-id</I> that refers to a type and in which 
the <I>nested-name-specifier</I>
depends on a <I>template-parameter</I> (14.6.2&nbsp;



 <A HREF="template.html#temp.dep">temp.dep</A>)
shall be prefixed by the keyword
<TT>typename</TT> to indicate that
the <I>qualified-id</I> denotes a type, forming an
<I>elaborated-type-specifier</I> (7.1.5.3&nbsp;



 <A HREF="dcl.html#dcl.type.elab">dcl.type.elab</A>). 
</BLOCKQUOTE>

<P>With:</P>

<BLOCKQUOTE>
The keyword <TT>typename</TT> can only be applied to a <I>qualified-id</I>. A
<I>qualified-id</I> that refers to a type and in which
the <I>nested-name-specifier</I>
depends on a <I>template-parameter</I> (14.6.2&nbsp;



 <A HREF="template.html#temp.dep">temp.dep</A>)
shall be prefixed by the keyword
<TT>typename</TT> to indicate that the <I>qualified-id</I>
denotes a type, forming
an <I>elaborated-type-specifier</I> (7.1.5.3&nbsp;



 <A HREF="dcl.html#dcl.type.elab">dcl.type.elab</A>).
If a <I>qualified-id</I> which
has been prefixed by the keyword <TT>typename</TT> does not
denote a type the program is ill-formed.
[ <I>Note:</I> The keyword is only required on a <I>qualified-id</I> within a
template declaration or definition in which the
<I>nested-name-specifier</I> depends on a <I>template-parameter</I>. ]
</BLOCKQUOTE>

<P>Remove 14.6&nbsp;



 <A HREF="template.html#temp.res">temp.res</A> paragraph 5:</P>

<BLOCKQUOTE>
The keyword <TT>typename</TT> shall only be used in template
declarations and definitions, including in the return type of a function template or
member function template, in the return type for the definition of a member function
of a class template or of a class nested within a class template, and in the
<I>type-specifier</I> for the definition of a static member of a class template or
of a class nested within a class template. The keyword <TT>typename</TT> shall be
applied only to qualified names, but those names need not be dependent. The keyword
<TT>typename</TT> shall be used only in contexts in which dependent names
can be used. This includes template declarations and definitions but excludes explicit
specialization declarations and explicit instantiation declarations. The keyword
<TT>typename</TT>
is not permitted in a <I>base-specifier</I> or in a <I>mem-initializer</I>; in these
contexts a <I>qualified-id</I> that depends on a <I>template-parameter</I> (temp.dep) is
implicitly assumed to be a type name.
</BLOCKQUOTE>

<P>
<B>Note:</B> the claim here that a qualified name preceded by
<TT>typename</TT> forms an elaborated type specifier conflicts with
the changes made in <A HREF="
     cwg_defects.html#254">issue 254</A> (see
N1376=02-0034), which introduces <I>typename-specifier</I>.</P>

<P>
<B>Notes from October 2003 meeting:</B>
</P>

<P>We considered whether <TT>typename</TT> should be allowed in more
places, and decided we only wanted to allow it in qualified
names (for now at least).</P>

<P>
<A HREF="
     cwg_defects.html#254">Core issue 254</A> changed
<I>elaborated-type-specifier</I> to <I>typename-specifier</I>.
It also changed 14.6&nbsp;



 <A HREF="template.html#temp.res">temp.res</A> paragraph 5, which
this proposed resolution deletes.  </P>

<P>See also <A HREF="
     cwg_defects.html#468">issue 468</A>.</P>

<P>
<B>Proposed resolution (October, 2004):</B>
</P>

<OL>

<LI>
<P>Change 14.6&nbsp;



 <A HREF="template.html#temp.res">temp.res</A> paragraph 3 as
follows:</P>

<BLOCKQUOTE>

<S>A</S> <B>When a</B> <I>qualified-id</I> <S>that refers to a
type and</S> in which the <I>nested-name-specifier</I> depends on a
<I>template-parameter</I> (14.6.2&nbsp;



 <A HREF="template.html#temp.dep">temp.dep</A>) <B>is
intended to refer to a type, it</B> shall be prefixed by the
keyword <TT>typename</TT> <S>to indicate that the qualified-id
denotes a type</S>, forming a <I>typename-specifier</I>. <B>If
the <I>qualified-id</I> in a <I>typename-specifier</I> does not
denote a type, the program is ill-formed.</B>

</BLOCKQUOTE>

</LI>

<LI>
<P>Change 14.6&nbsp;



 <A HREF="template.html#temp.res">temp.res</A> paragraph 5 as
follows:</P>

<BLOCKQUOTE>

<S>The keyword <TT>typename</TT> shall only be used in template
declarations and definitions, including in the return type of a
function template or member function template, in the return type
for the definition of a member function of a class template or of
a class nested within a class template, and in the
<I>type-specifier</I> for the definition of a static member of a
class template or of a class nested within a class template. The
keyword <TT>typename</TT> shall be applied only to qualified
names, but those names need not be dependent. The keyword
<TT>typename</TT> shall be used only in contexts in which
dependent names can be used. This includes template declarations
and definitions but excludes explicit specialization declarations
and explicit instantiation declarations.</S> A qualified name
used as the name in a <I>mem-initializer-id</I>, a
<I>base-specifier</I>, or an <I>elaborated-type-specifier</I> is
implicitly assumed to name a type, without the use of the
<TT>typename</TT> keyword. [<I>Note:</I> the <TT>typename</TT>
keyword is not permitted by the syntax of these
constructs. &mdash;<I>end note</I>]

</BLOCKQUOTE>

</LI>

</OL>

<BR>
<BR>
<HR>
<A NAME="409"></A>
<H4>409.
  
Obsolete paragraph missed by changes for issue 224
</H4>
<B>Section: </B>14.6&nbsp;



 <A HREF="template.html#temp.res">temp.res</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>John Spicer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>18 Apr 2003<BR>


<P>[Voted into WP at October 2004 meeting.]</P>

<P>Paragraph 6 of 14.6&nbsp;



 <A HREF="template.html#temp.res">temp.res</A> is obsolete as result of
<A HREF="
     cwg_defects.html#224">issue 224</A>, and needs to be revised.</P>
<BLOCKQUOTE>
Within  the definition of a class template or within the definition of
a member of a class template, the keyword  typename  is  not  required
when referring to the unqualified name of a previously declared member
of the class template that declares  a  type.   The  keyword  typename
shall always be specified when the member is referred to using a qual-
ified name, even if the qualifier is simply the class  template  name.
[<I>Example:</I>
<PRE>
  template&lt;class T&gt; struct A {
      typedef int B;
      A::B b;                     // ill-formed: typename required before A::B
      void f(A&lt;T&gt;::B);            // ill-formed: typename required before A&lt;T&gt;::B
      typename A::B g();          // OK
  };
</PRE>
]
</BLOCKQUOTE>

<P>
<B>Proposed Resolution:</B>
</P>
<P>
Change 14.6&nbsp;



 <A HREF="template.html#temp.res">temp.res</A> paragraph 6 as follows</P>
<BLOCKQUOTE>
Within the definition of a class template or within the definition of
a member of a class template, the keyword <TT>typename</TT> is not
required when referring to the unqualified name of a previously
declared member of the class template that declares a type.
<S>The keyword <TT>typename</TT> shall always be specified when the
member is referred to using a qualified name, even if the qualifier is
simply the class template name.</S> [Example:

<PRE>
template&lt;class T&gt; struct A {
    typedef int B;
    B b;                      // ok, no typename required
<S>    A::B b;                   //  ill-formed: typename required before  A::B
    void f(A&lt;T&gt;::B);          //  ill-formed: typename required before  A&lt;T&gt;::B
    typename A::B g();        //  OK</S>
};
</PRE>

<S>The keyword typename is required whether the qualified name is A or
A&lt;T&gt; because A or A&lt;T&gt; are synonyms within a class template with
the parameter list &lt;T&gt;. </S>]
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="559"></A>
<H4>559.
  
Editing error in issue 382 resolution
</H4>
<B>Section: </B>14.6&nbsp;



 <A HREF="template.html#temp.res">temp.res</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>11 February 2006<BR>


<P>[Voted into WP at April, 2006 meeting.]</P>

<P>Part of the resolution for <A HREF="
     cwg_defects.html#224">issue 224</A> was
the addition of the phrase &ldquo;but does not refer to a member of
the current instantiation&rdquo; to 14.6&nbsp;



 <A HREF="template.html#temp.res">temp.res</A>
paragraph 3.  When the resolution of <A HREF="
     cwg_defects.html#382">issue 382</A>
was added to the current working draft, however, that phrase was
inadvertently removed.  Equivalent phrasing should be restored.</P>

<P>
<B>Proposed resolution (April, 2006):</B>
</P>

<P>Replace the first sentence of 14.6&nbsp;



 <A HREF="template.html#temp.res">temp.res</A> paragraph 3
with the following text:</P>

<BLOCKQUOTE>

When a <I>qualified-id</I> is intended to refer to a type that is not
a member of the current instantiation (14.6.2.1&nbsp;



 <A HREF="template.html#temp.dep.type">temp.dep.type</A>) and its <I>nested-name-specifier</I> depends on a
<I>template-parameter</I> (14.6.2&nbsp;



 <A HREF="template.html#temp.dep">temp.dep</A>), it shall be
prefixed by the keyword <TT>typename</TT>, forming
a <I>typename-specifier</I>.

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="224"></A>
<H4>224.
  
Definition of dependent names
</H4>
<B>Section: </B>14.6.2.1&nbsp;



 <A HREF="template.html#temp.dep.type">temp.dep.type</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Derek Inglis
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>30 Nov 1999<BR>


<P>[Moved to DR at 10/01 meeting.]</P>



<P>The definition of when a type is dependent, given in
14.6.2.1&nbsp;



 <A HREF="template.html#temp.dep.type">temp.dep.type</A>, is essentially syntactic: if the
reference is a <I>qualified-id</I> and one of the <I>class-name</I>s
in the <I>nested-name-specifier</I> is dependent, the type is
dependent.  This approach leads to surprising results:</P>

<PRE>
    template &lt;class T&gt; class X {
        typedef int I;
	I a;                 // non-dependent
        typename X&lt;T&gt;::I b;  // dependent
        typename X::I c;     // dependent (X is equivalent to X&lt;T&gt;)
    };
</PRE>

<P>
<B>Suggested resolution:</B>
</P>

<P>The decision on whether a name is dependent or non-dependent should
be based on lookup, not on the form of the name: if the name can be
looked up in the definition context and cannot be anything else as the
result of specialization, the name should be non-dependent.</P>

<P>See papers J16/00-0028 = WG21 N1251 and
J16/00-0056 = WG21 N1279.</P>

<P>
<B>Proposed resolution (10/00):</B>
</P>

<OL>

<LI>
<P>Replace section 14.6.2.1&nbsp;



 <A HREF="template.html#temp.dep.type">temp.dep.type</A> with the
following:

<BLOCKQUOTE>

<P>In the definition of a class template, a nested class of a class
template, a member of a class template, or a member of a nested class
of a class template, a name refers to the <I>current
instantiation</I> if it is</P>

<UL>

<LI>the injected-class-name (clause 9&nbsp;



 <A HREF="class.html#class">class</A>) of the
class template or nested class,</LI>

<LI>in the definition of a primary class template, the name of the
class template followed by the template argument list of the
primary template (as described below) enclosed in &lt;&gt;,</LI>

<LI>in the definition of a nested class of a class template,
the name of the nested class referenced as a member of the
current instantiation, or</LI>

<LI>in the definition of a partial specialization, the name of
the class template followed by the template argument list of
the partial specialization enclosed in &lt;&gt;.</LI>

</UL>

<P>The template argument list of a primary template is a
template argument list in which the n<SUP>th</SUP> template
argument has the value of the n<SUP>th</SUP> template
parameter of the class template.</P>

<P>A template argument that is equivalent to a template
parameter (i.e., has the same constant value or the same type
as the template parameter) can be used in place of that
template parameter in a reference to the current
instantiation.  In the case of a nontype template argument,
the argument must have been given the value of the
template parameter and not an expression involving the
template parameter.</P>

<P>[<I>Example:</I>
</P>

<PRE>
template &lt;class T&gt; class A {
    A* p1;      // A is the current instantiation
    A&lt;T&gt;* p2;   // A&lt;T&gt; is the current instantiation
    A&lt;T*&gt; p3;   // A&lt;T*&gt; is not the current instantiation
    ::A&lt;T&gt;* p4; // ::A&lt;T&gt; is the current instantiation
    class B {
	B* p1;        // B is the current instantiation
	A&lt;T&gt;::B* p2;  // A&lt;T&gt;::B is the current instantiation
	typename A&lt;T*&gt;::B* p3; // A&lt;T*&gt;::B is not the
			     // current instantiation
    };
};

template &lt;class T&gt; class A&lt;T*&gt; {
    A&lt;T*&gt;* p1;  // A&lt;T*&gt; is the current instantiation
    A&lt;T&gt;* p2;   // A&lt;T&gt; is not the current instantiation
};

template &lt;class T1, class T2, int I&gt; struct B {
    B&lt;T1, T2, I&gt;*	b1;        // refers to the current instantiation
    B&lt;T2, T1, I&gt;*	b2;        // not the current instantiation
    typedef T1 my_T1;
    static const int my_I = I;
    static const int my_I2 = I+0;
    static const int my_I3 = my_I;
    B&lt;my_T1, T2, my_I&gt;* b3;  // refers to the current instantiation
    B&lt;my_T1, T2, my_I2&gt;* b4; // not the current instantiation
    B&lt;my_T1, T2, my_I3&gt;* b5; // refers to the current instantiation
};
</PRE>

<P>&mdash;<I>end example</I>]</P>

<P>A name is a <I>member of the current instantiation</I> if it is</P>

<UL>

<LI>An unqualified name that, when looked up, refers to a member
of a class template.  [<I>Note:</I> This can only occur when
looking up a name in a scope enclosed by the definition of a
class template.]</LI>

<LI>A <I>qualified-id</I> in which the <I>nested-name-specifier</I>
refers to the current instantiation.</LI>

</UL>

<P>[<I>Example:</I>
</P>

<PRE>
template &lt;class T&gt; class A {
    static const int i = 5;
    int n1[i];        // i refers to a member of the current instantiation 
    int n2[A::i];     // A::i refers to a member of the current instantiation 
    int n3[A&lt;T&gt;::i];  // A&lt;T&gt;::i refers to a member of the current instantiation 
    int f();
};

template &lt;class T&gt; int A&lt;T&gt;::f()
{
    return i;  // i refers to a member of the current instantiation
}
</PRE>

<P>&mdash;<I>end example</I>]</P>

<P>A name is a <I>member of an unknown specialization</I> if the
name is a <I>qualified-id</I> in which the
<I>nested-name-specifier</I> names a dependent type that is not
the current instantiation.</P>

<P>A type is dependent if it is</P>

<UL>

<LI>a template parameter,</LI>

<LI>a member of an unknown specialization,</LI>

<LI>a nested class that is a member of the current
instantiation,</LI>

<LI>a cv-qualified type where the cv-unqualified type is dependent,</LI>

<LI>a compound type constructed from any dependent type,</LI>

<LI>an array type constructed from any dependent type or whose
size is specified by a constant expression that is value-dependent, or</LI>

<LI>a <I>template-id</I> in which either the template name is a
template parameter or any of the template arguments is a dependent
type or an expression that is type-dependent or value-dependent.</LI>

</UL>

<P>[<I>Note:</I> Because typedefs to not introduce new types, but
instead simply refer to other types, a name that refers to a
typedef that is a member of the current instantiation is dependent
only if the type referred to is dependent.]</P>

</BLOCKQUOTE>

</P>
</LI>

<LI>
<P>In 14.6.2.2&nbsp;



 <A HREF="template.html#temp.dep.expr">temp.dep.expr</A> paragraph 3, replace</P>

<BLOCKQUOTE>

<UL>
<LI>a <I>nested-name-specifier</I> that contains a
<I>class-name</I> that names a dependent type.</LI>
</UL>

</BLOCKQUOTE>

<P>with</P>

<BLOCKQUOTE>

<UL>
<LI>a <I>nested-name-specifier</I> or <I>qualified-id</I> that
names a member of an unknown specialization.</LI>
</UL>

</BLOCKQUOTE>

</LI>

<LI>
<P>In 14.6.2.2&nbsp;



 <A HREF="template.html#temp.dep.expr">temp.dep.expr</A>, add the following
paragraph:</P>

<BLOCKQUOTE>

A class member access expression (5.2.5&nbsp;



 <A HREF="expr.html#expr.ref">expr.ref</A>) is
type-dependent if the type of the referenced member is dependent.
[<I>Note:</I> In an expression of the form <TT>x.y</TT> or
<TT>xp-&gt;y</TT> the type of the expression is usually the type
of the member <TT>y</TT> of the class of <TT>x</TT> (or the class
pointed to by <TT>xp</TT>).  However, if <TT>x</TT> or <TT>xp</TT>
refers to a dependent type that is not the current instantiation,
the type of <TT>y</TT> is always dependent.  If <TT>x</TT> or
<TT>xp</TT> refers to a non-dependent type or refers to the
current instantiation, the type of <TT>y</TT> is the type of the
class member access expression.]

</BLOCKQUOTE>

</LI>

<LI>
<P>In 14.6&nbsp;



 <A HREF="template.html#temp.res">temp.res</A> paragraph 3, replace</P>

<BLOCKQUOTE>

A <I>qualified-name</I> that refers to a type and that depends
on a <I>template-parameter</I> (14.6.2&nbsp;



 <A HREF="template.html#temp.dep">temp.dep</A>) shall
be prefixed by the keyword <TT>typename</TT>.

</BLOCKQUOTE>

<P>with</P>

<BLOCKQUOTE>

A <I>qualified-id</I> that refers to a type and that depends on
a <I>template-parameter</I> (14.6.2&nbsp;



 <A HREF="template.html#temp.dep">temp.dep</A>) but
does not refer to a member of the current instantiation shall be
prefixed by the keyword <TT>typename</TT>.

</BLOCKQUOTE>

<P>Note: the wording for this paragraph was changed in TC1.  The
words shown here are the pre-TC1 words.</P>

</LI>

<LI>
<P>In 14.2&nbsp;



 <A HREF="template.html#temp.names">temp.names</A> paragraph 4, replace</P>

<BLOCKQUOTE>

When the name of a member template specialization appears after
<TT>.</TT> or <TT>-&gt;</TT> in a <I>postfix-expression</I>, or
after a <I>nested-name-specifier</I> in a <I>qualified-id</I>,
and the <I>postfix-expression</I> or <I>qualified-id</I> explicitly
depends on a <I>template-parameter</I> (14.6.2&nbsp;



 <A HREF="template.html#temp.dep">temp.dep</A>),
the member template name must be prefixed by the keyword
<TT>template</TT>.  Otherwise the name is assumed to name a
non-template.

</BLOCKQUOTE>

<P>with</P>

<BLOCKQUOTE>

When the name of a member template specialization appears after
<TT>.</TT> or <TT>-&gt;</TT> in a <I>postfix-expression</I>, or
after a <I>nested-name-specifier</I> in a <I>qualified-id</I>,
and the <I>postfix-expression</I> or <I>qualified-id</I> explicitly
depends on a <I>template-parameter</I> (14.6.2&nbsp;



 <A HREF="template.html#temp.dep">temp.dep</A>)
but does not refer to a member of the current instantiation
(14.6.2.1&nbsp;



 <A HREF="template.html#temp.dep.type">temp.dep.type</A>), the member template name must
be prefixed by the keyword <TT>template</TT>.  Otherwise the name
is assumed to name a non-template.

</BLOCKQUOTE>

</LI>

<LI>
<P>In 14.6.1&nbsp;



 <A HREF="template.html#temp.local">temp.local</A> paragraph 2, remove the
following text, which was added for <A HREF="
     cwg_defects.html#108">issue 108</A>.
The updated definition of dependent name now addresses this case.</P>

<BLOCKQUOTE>

<P>Within the scope of a class template, when the unqualified name of
a nested class of the class template is referred to, it is
equivalent to the name of the nested class qualified by the name
of the enclosing class template.  [<I>Example:</I>
</P>

<PRE>
template &lt;class T&gt; struct A {
	class B {};
	// B is equivalent to A::B, which is equivalent to A&lt;T&gt;::B,
	// which is dependent.
	class C : B { };
};
</PRE>

<P>&mdash;<I>end example</I>]</P>

</BLOCKQUOTE>

</LI>

</OL>

<BR>
<BR>
<HR>
<A NAME="447"></A>
<H4>447.
  
Is offsetof type-dependent?
</H4>
<B>Section: </B>14.6.2.3&nbsp;



 <A HREF="template.html#temp.dep.constexpr">temp.dep.constexpr</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mark Mitchell
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>7 Jan 2004<BR>


<P>[Voted into WP at October 2005 meeting.]</P>

<P>As far as I can tell, the standard doesn't say whether "offsetof(...)"
is type-dependent.  In the abstract, it shouldn't be -- an "offsetof"
expression is always of type "size_t". But the standard doesn't say to
what the definition of the macro is, so I don't think one can deduce
that it will always be considered non-dependent by a conforming
compiler.</P>

<P>
<U>John Spicer:</U>
(1) I agree that you can't know if offsetof is dependent because you
don't know what it expands to.
(2) In principle, offsetof should be like sizeof -- it is value-dependent
if its argument is type-dependent.</P>

<P>
<U>Mark Mitchell:</U>
I think we should say that:
(a) offsetof is not type-dependent, and
(b) offsetof is value dependent iff the first argument is type-dependent</P>

<P>Everyone is using slightly different builtins to implement this
functionality, and I don't think that there's any guarantee that they're all
behaving the same here.</P>

<P>
<B>Notes from the March 2004 meeting:</B>
</P>

<P>Note that any such requirement would be in the library section,
not core.</P>

<P>
<B>Proposed resolution (October, 2004):</B>
</P>

<OL>

<LI>
<P>At the end of 14.6.2.2&nbsp;



 <A HREF="template.html#temp.dep.expr">temp.dep.expr</A> paragraph
4, add after the list that ends with <TT>throw</TT>
<I>assignment-expression</I>:</P>

<BLOCKQUOTE>

[<I>Note:</I> For the standard library macro <TT>offsetof</TT>,
see 18.1&nbsp;



 <A HREF="lib-support.html#lib.support.types">lib.support.types</A>. &mdash;<I>end note</I>]

</BLOCKQUOTE>

</LI>

<LI>
<P>At the end of 14.6.2.3&nbsp;



 <A HREF="template.html#temp.dep.constexpr">temp.dep.constexpr</A> paragraph
2, add after the list that ends with
<TT>sizeof(</TT><I>type-id</I><TT>)</TT>:</P>

<BLOCKQUOTE>

[<I>Note:</I> For the standard library macro <TT>offsetof</TT>,
see 18.1&nbsp;



 <A HREF="lib-support.html#lib.support.types">lib.support.types</A>. &mdash;<I>end note</I>]

</BLOCKQUOTE>

</LI>

<LI>
<P>In 18.1&nbsp;



 <A HREF="lib-support.html#lib.support.types">lib.support.types</A> paragraph 4, replace</P>

<BLOCKQUOTE>

The macro <TT>offsetof</TT> accepts a restricted set of
<I>type</I> arguments in this International Standard. If
<I>type</I> is not a POD structure or a POD union the results are
undefined. The result of applying the <TT>offsetof</TT> macro to
a field that is a static data member or a function member is
undefined.

</BLOCKQUOTE>

<P>with</P>

<BLOCKQUOTE>

The macro <TT>offsetof(</TT><I>type</I><TT>,</TT>
<I>member-designator</I><TT>)</TT> accepts a restricted set of
<I>type</I> arguments in this International Standard. If
<I>type</I> is not a POD structure or a POD union (clause
9&nbsp;



 <A HREF="class.html#class">class</A>), the results are undefined. The
expression <TT>offsetof(</TT><I>type</I><TT>,</TT>
<I>member-designator</I><TT>)</TT> is never type-dependent
(14.6.2.2&nbsp;



 <A HREF="template.html#temp.dep.expr">temp.dep.expr</A>) and it is value-dependent
(14.6.2.3&nbsp;



 <A HREF="template.html#temp.dep.constexpr">temp.dep.constexpr</A>) if and only if <I>type</I> is
dependent. The result of applying the <TT>offsetof</TT> macro to
a field that is a static data member or a function member is
undefined.

</BLOCKQUOTE>

<P>
<I>[Note: the original wording shown here reflects the
resolutions of library issues 306 and 449.]</I>
</P>

</LI>

</OL>

<BR>
<BR>
<HR>
<A NAME="197"></A>
<H4>197.
  
Issues with two-stage lookup of dependent names
</H4>
<B>Section: </B>14.6.4.2&nbsp;



 <A HREF="template.html#temp.dep.candidate">temp.dep.candidate</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Derek Inglis
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>26 Jan 2000<BR>



<P>[Voted into WP at October 2005 meeting.]</P>



<P>The example in
14.6&nbsp;



 <A HREF="template.html#temp.res">temp.res</A>
 paragraph 9 is incorrect,
according to 14.6.4.2&nbsp;



 <A HREF="template.html#temp.dep.candidate">temp.dep.candidate</A>
.  The
example reads,</P>

<PRE>
    void f(char);

    template &lt;class T&gt; void g(T t)
    {
        f(1);        // f(char);
        f(T(1));     // <I>dependent</I>
        f(t);        // <I>dependent</I>
        dd++;        // <I>not dependent</I>
                     // <I>error: declaration for dd not found</I>
    }

    void f(int);

    double dd;
    void h()
    {
        g(2);        // <I>will cause one call of </I>f(char)<I> followed</I>
                     // <I>by two calls of </I>f(int)
        g('a');      // <I>will cause three calls of </I>f(char)
    }
</PRE>

Since 14.6.4.2&nbsp;



 <A HREF="template.html#temp.dep.candidate">temp.dep.candidate</A>
 says that
only Koenig lookup is done from the instantiation context, and since
3.4.2&nbsp;



 <A HREF="basic.html#basic.lookup.argdep">basic.lookup.argdep</A>
 says that
fundamental types have no associated namespaces, either the example is
incorrect (and <TT>f(int)</TT> will never be called) or the
specification in 14.6.4.2&nbsp;



 <A HREF="template.html#temp.dep.candidate">temp.dep.candidate</A>

is incorrect.

<P>
<B>Notes from 04/00 meeting:</B>
</P>

<P>The core working group agreed that the example as written is
incorrect and should be reformulated to use a class type instead of a
fundamental type.  It was also decided to open a new issue dealing
more generally with Koenig lookup and fundamental types.</P>

<P>(See also issues <A HREF="
     cwg_defects.html#213">213</A> and
<A HREF="
     cwg_active.html#225">225</A>.)</P>

<P>
<B>Proposed resolution (April, 2005):</B>
</P>

<P>Change the example in 14.6&nbsp;



 <A HREF="template.html#temp.res">temp.res</A> paragraph 9 as
follows:</P>

<PRE>
    void f(char);

    template &lt;class T&gt; void g(T t)
    {
        f(1);        // f(char);
        f(T(1));     // <I>dependent</I>
        f(t);        // <I>dependent</I>
        dd++;        // <I>not dependent</I>
                     // <I>error: declaration for </I>dd<I> not found</I>
    }

    <B>enum E { e };</B>
    void f(<S>int</S><B>E</B>);

    double dd;
    void h()
    {
        g(<S>2</S><B>e</B>);       // <I>will cause one call of </I>f(char)<I> followed</I>
                     // <I>by two calls of </I>f(<S>int</S><B>E</B>)
        g('a');      // <I>will cause three calls of</I> f(char)
    }
</PRE>

<BR>
<BR>
<HR>
<A NAME="387"></A>
<H4>387.
  
Errors in example in 14.6.5
</H4>
<B>Section: </B>14.6.5&nbsp;



 <A HREF="template.html#temp.inject">temp.inject</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Aleksey Gurtovoy
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>27 Oct 2002<BR>


<P>[Voted into WP at March 2004 meeting.]</P>

<P>The example in 14.6.5&nbsp;



 <A HREF="template.html#temp.inject">temp.inject</A>
paragraph 2 is incorrect:</P>
<PRE>
  template&lt;typename T&gt; class number {
      number(int);
      //...
      friend number gcd(number&amp; x, number&amp; y) { /* ... */ }
      //...
  };

  void g()
  {
      number&lt;double&gt; a(3), b(4);
      //...
      a = gcd(a,b);   // finds gcd because number&lt;double&gt; is an
                      // associated class, making gcd visible
                      // in its namespace (global scope)
      b = gcd(3,4);   // ill-formed; gcd is not visible
  }
</PRE>
<P>Regardless of the last statement ("b = gcd(3,4);"), the above code is
ill-formed:</P>

<P>  a) number's constructor is private;</P>
<P>  b) the definition of (non-void) friend 'gcd' function does not
contain a return statement.</P>

<P>
<B>Proposed resolution (April 2003):</B>
</P>

<P>
Replace the example in 14.6.5&nbsp;



 <A HREF="template.html#temp.inject">temp.inject</A>
paragraph 2</P>

<BLOCKQUOTE>
<PRE>
  template&lt;typename T&gt; class number {
          number(int);
          //...
          friend number gcd(number&amp; x, number&amp; y) { /* ... */ }
          //...
  };

  void g()
  {
          number&lt;double&gt; a(3), b(4);
          //...
          a = gcd(a,b);           //  finds  gcd  because  number&lt;double&gt;  is an
                                  //  associated class, making  gcd  visible
                                  //  in its namespace (global scope)
          b = gcd(3,4);           //  ill-formed;  gcd  is not visible
  }
</PRE>
</BLOCKQUOTE>

by

<BLOCKQUOTE>
<PRE>
  template&lt;typename T&gt; class number {
     public:
          number(int);
          //...
          friend number gcd(number x, number y) { return 0; }
     private:
          //...
  };

  void g()
  {
          number&lt;double&gt; a(3), b(4);
          //...
          a = gcd(a,b);           //  finds  gcd  because  number&lt;double&gt;  is an
                                  //  associated class, making  gcd  visible
                                  //  in its namespace (global scope)
          b = gcd(3,4);           //  ill-formed;  gcd  is not visible
  }
</PRE>
</BLOCKQUOTE>

<P>
<I>Drafting note: Added "return" to the friend function, removed
references in gcd arguments, added access specifiers.</I>
</P>

<BR>
<BR>
<HR>
<A NAME="259"></A>
<H4>259.
  
Restrictions on explicit specialization and instantiation
</H4>
<B>Section: </B>14.7&nbsp;



 <A HREF="template.html#temp.spec">temp.spec</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Matt Austern
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>2 Nov 2000<BR>


<P>[Moved to DR at 4/02 meeting.]</P>



<P>According to 14.7&nbsp;



 <A HREF="template.html#temp.spec">temp.spec</A> paragraph 5,</P>

<BLOCKQUOTE>

No program shall explicitly instantiate any template more than once,
both explicitly instantiate and explicitly specialize a template, or
specialize a template more than once for a given set of
<I>template-argument</I>s.

</BLOCKQUOTE>

<P>This rule has an impact on library issue 120.  Library authors
would like to have the freedom to specialize (or not) various
library functions without having to document their choices, while
users need the flexibility to explicitly instantiate library
functions in certain translation units.</P>

<P>If this rule could be slightly weakened, it would reduce the need
for constraining either the library author or the programmer.  For
instance, the rule might be recast to say that if a specialization is
followed by an explicit instantiation in the same translation unit,
the explicit instantiation is ignored.  A specialization and an
explicit instantiation of the same template in two different
translation units would still be an error, no diagnostic required.</P>

<P>
<B>Proposed resolution (04/01):</B>
</P>

<OL>
<LI>
<P>Replace the first sentence of 14.7&nbsp;



 <A HREF="template.html#temp.spec">temp.spec</A>
paragraph 5,</P>

<BLOCKQUOTE>

No program shall explicitly instantiate any template more
than once, both explicitly instantiate and explicitly
specialize a template, or specialize a template more than
once for a given set of <I>template-argument</I>s.

</BLOCKQUOTE>

<P>by</P>

<BLOCKQUOTE>

For a given template and a given set of <I>template-argument</I>s,

<UL>
<LI>an explicit instantiation shall appear at most once in a
program,</LI>

<LI>an explicit specialization shall be defined at most once
according to 3.2&nbsp;



 <A HREF="basic.html#basic.def.odr">basic.def.odr</A> in a program, and</LI>

<LI>both an explicit instantiation and a declaration of an
explicit specialization shall not appear in a program unless
the explicit instantiation follows a declaration of the explicit
specialization.</LI>

</UL>

</BLOCKQUOTE>
</LI>

<LI>
<P>Replace 14.7.2&nbsp;



 <A HREF="template.html#temp.explicit">temp.explicit</A> paragraph 4,</P>

<BLOCKQUOTE>

The definition of a non-exported function template, a non-exported
member function template, or a non-exported member function or
static data member of a class template shall be present in every
translation unit in which it is explicitly instantiated.

</BLOCKQUOTE>

<P>by</P>

<BLOCKQUOTE>

For a given set of template parameters, if an explicit
instantiation of a template appears after a declaration of
an explicit specialization for that template, the explicit
instantiation has no effect.  Otherwise, the definition of a
non-exported function template, a non-exported member
function template, or a non-exported member function or static
data member of a class template shall be present in every
translation unit in which it is explicitly instantiated.

</BLOCKQUOTE>
</LI>

</OL>

<BR>
<BR>
<HR>
<A NAME="63"></A>
<H4>63.
  
Class instantiation from pointer conversion to void*, null and self
</H4>
<B>Section: </B>14.7.1&nbsp;



 <A HREF="template.html#temp.inst">temp.inst</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Adamczyk
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>13 Oct 1998<BR>



<P>[Moved to DR at October 2002 meeting.]</P>

<P>A template is implicitly instantiated because of a "pointer conversion"
on an argument. This was intended to include related-class conversions,
but it also inadvertently includes conversions to <TT>void*, </TT>null
pointer conversions, cv-qualification conversions and the identity conversion.</P>

<P>It is not clear whether a <TT>reinterpret_cast</TT> of a pointer should
cause implicit instantiation.</P>

<P>
<B>Proposed resolution (10/01):</B> Replace
14.7.1&nbsp;



 <A HREF="template.html#temp.inst">temp.inst</A>
 paragraph 4, up to the
example, with the following:</P>
<BLOCKQUOTE>
A class template specialization is implicitly instantiated if the
class type is used in a context that requires a completely-defined
object type or if the completeness of the class type might affect the
semantics of the program.  [<I>Note:</I> in particular, if the
semantics of an expression depend on the member or base class lists
of a class template specialization, the class template specialization
is implicitly generated.  For instance, deleting a pointer to class
type depends on whether or not the class declares a destructor, and
conversion between pointer to class types depends on the inheritance
relationship between the two classes involved. ]
</BLOCKQUOTE>

<P>This version differs from the previous version is its use of the
word "might" in the first sentence.</P>

<P>(See also <A HREF="
     cwg_active.html#212">issue 212</A>.)</P>

<BR>
<BR>
<HR>
<A NAME="525"></A>
<H4>525.
  
Missing <TT>*</TT> in example
</H4>
<B>Section: </B>14.7.1&nbsp;



 <A HREF="template.html#temp.inst">temp.inst</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>25 July 2005<BR>


<P>[Voted into WP at April, 2006 meeting.]</P>

<P>The example in 14.7.1&nbsp;



 <A HREF="template.html#temp.inst">temp.inst</A> paragraph 4 has a
typographical error: the third parameter of function <TT>g</TT>
should be <TT>D&lt;double&gt;* ppp</TT>, but it is missing the
<TT>*</TT>:</P>

<PRE>
  template &lt;class T&gt; class B { /* ... */ };
  template &lt;class T&gt; class D : public B&lt;T&gt; { /* ... */ };
  void f(void*);
  void f(B&lt;int &gt;*);

  void g(D&lt;int&gt;* p, D&lt;char&gt;* pp, D&lt;double&gt; ppp)
  {
    f(p);             //<SPAN STYLE="font-family:Times"><I> instantiation of </I><TT>D&lt;int&gt;</TT><I> required: call </I><TT>f(B&lt;int&gt;*)</TT></SPAN>

    B&lt;char&gt;* q = pp;  //<SPAN STYLE="font-family:Times"><I> instantiation of </I><TT>D&lt;char&gt;</TT><I> required:</I></SPAN>
                      //<SPAN STYLE="font-family:Times"><I> convert </I><TT>D&lt;char&gt;*</TT><I> to </I><TT>B&lt;char&gt;*</TT></SPAN>
    delete ppp;       //<SPAN STYLE="font-family:Times"><I> instantiation of </I><TT>D&lt;double&gt;</TT><I> required</I></SPAN>
  }
</PRE>

<P>
<B>Proposed resolution (October, 2005):</B>
</P>

<P>As suggested.</P>

<BR>
<BR>
<HR>
<A NAME="237"></A>
<H4>237.
  
Explicit instantiation and base class members
</H4>
<B>Section: </B>14.7.2&nbsp;



 <A HREF="template.html#temp.explicit">temp.explicit</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Christophe de Dinechin
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>28 Jul 2000<BR>


<P>[Voted into WP at October 2005 meeting.]</P>



<P>In 14.7.2&nbsp;



 <A HREF="template.html#temp.explicit">temp.explicit</A> paragraph 7 we read:</P>

<BLOCKQUOTE>
 The explicit instantiation of a class template specialization 
implies the instantiation of all of its members not previously 
explicitly specialized in the translation unit containing the 
explicit instantiation.
</BLOCKQUOTE>

<P>Is "member" intended to mean "non-inherited member?"
If yes, maybe it should be clarified since
10&nbsp;



 <A HREF="derived.html#class.derived">class.derived</A> paragraph 1 says,</P>

<BLOCKQUOTE>
Unless redefined in the derived class, members of a 
base class are also considered to be members of the derived 
class. 

</BLOCKQUOTE>

<P>
<B>Proposed resolution (October, 2004):</B>
</P>

<P>Fixed by the resolution of <A HREF="
     cwg_defects.html#470">issue 470</A>.</P>

<BR>
<BR>
<HR>
<A NAME="470"></A>
<H4>470.
  
Instantiation of members of an explicitly-instantiated class template
</H4>
<B>Section: </B>14.7.2&nbsp;



 <A HREF="template.html#temp.explicit">temp.explicit</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Matt Austern
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>11 May 2004<BR>


<P>[Voted into WP at October 2005 meeting.]</P>


<P>14.7.2&nbsp;



 <A HREF="template.html#temp.explicit">temp.explicit</A> paragraph 7 says,</P>

<BLOCKQUOTE>
The explicit instantiation of a class template specialization
implies the instantiation of all of its members not previously
explicitly specialized in the translation unit containing the
explicit instantiation.
</BLOCKQUOTE>

<P>It's not clear whether this &ldquo;implied&rdquo;
instantiation is implicit or explicit instantiation.  It makes a
difference in cases like the following:</P>

<PRE>
    template &lt;typename T&gt; struct foo {
        struct bar { };
    };

    template struct foo&lt;int&gt;;         // #1

    template struct foo&lt;int&gt;::bar;    // #2
</PRE>

<P>If the instantiation of <TT>foo&lt;int&gt;::bar</TT> implied
by <TT>#1</TT> is implicit, the explicit instantiation in
<TT>#2</TT> is well-formed.  Otherwise, <TT>#2</TT> violates the
requirement in 14.7&nbsp;



 <A HREF="template.html#temp.spec">temp.spec</A> that</P>

<BLOCKQUOTE>
No program shall explicitly instantiate any template more than
once ... for a given set of <I>template-argument</I>s.
</BLOCKQUOTE>

<P>It's also unclear whether the implied instantiation applies
only to direct members of the class template or to inherited
members, as well.</P>

<P>
<U>John Spicer:</U> I have always interpreted this as meaning
only the members declared in the class, not those inherited from
other classes.  This is what EDG does, and appears to be what
g++, Microsoft and Sun do, too.  I also think this is the correct
thing for the Standard to require.  If I were to derive a class
from a class in the standard library, an explicit instantiation
of my class should not cause the explicit instantiation of things
in the standard library (because the library might provide such
explicit instantiations, thus causing my program to run afoul of
the "can't instantiate more than once" rule).</P>

<P>
<B>Proposed resolution (October, 2004):</B>
</P>

<P>Change 14.7.2&nbsp;



 <A HREF="template.html#temp.explicit">temp.explicit</A> paragraph 7 as follows:</P>

<BLOCKQUOTE>

The explicit instantiation of a class template specialization
<S>implies the instantiation of all</S> <B>also explicitly
instantiates each</B> of its members <S>not</S> <B>(not including
members inherited from base classes) whose definition is visible at
the point of instantiation and that has not been</B> previously
explicitly specialized in the translation unit containing the explicit
instantiation.

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="44"></A>
<H4>44.
  
Member specializations
</H4>
<B>Section: </B>14.7.3&nbsp;



 <A HREF="template.html#temp.expl.spec">temp.expl.spec</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Nathan Myers
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>19 Sep 1998<BR>



<P>[Moved to DR at 4/01 meeting.]</P>



<P>Some compilers reject the following:</P>
<PRE>
    struct A {
        template &lt;int I&gt; void f();
        template &lt;&gt; void f&lt;0&gt;();
    };
</PRE>
on the basis of 14.7.3&nbsp;



 <A HREF="template.html#temp.expl.spec">temp.expl.spec</A>

paragraph 2:
<BLOCKQUOTE>An explicit specialization shall be declared in the namespace
of which the template is a member, or, for member templates, in the namespace
of which the enclosing class or enclosing class template is a member. An
explicit specialization of a member function, member class or static data
member of a class template shall be declared in the namespace of which
the class template is a member. ...</BLOCKQUOTE>
claiming that the specialization above is not "in the namespace of which
the enclosing class ... is a member". Elsewhere, declarations are sometimes
required to be "at" or "in" "namespace scope", which is not what it says
here. Paragraph 17 says:
<BLOCKQUOTE>A member or a member template may be nested within many enclosing
class templates. If the declaration of an explicit specialization for such
a member appears in namespace scope, the member declaration shall be preceded
by a <TT>template&lt;&gt;</TT> for each
enclosing class template that is explicitly
specialized.</BLOCKQUOTE>
The qualification "if the declaration ... appears in namespace scope",
implies that it might appear elsewhere. The only other place I can think
of for a member specialization is in class scope.

<P>Was it the intent of the committee to forbid the construction above?
(Note that A itself is not a template.) If so, why?</P>

<P>
<B>Proposed resolution (04/01):</B> In-class specializations
of member templates are not allowed. In
14.7.3&nbsp;



 <A HREF="template.html#temp.expl.spec">temp.expl.spec</A>
 paragraph 17, replace</P>

<BLOCKQUOTE>
If the declaration of an explicit specialization for such a member
appears in namespace scope...
</BLOCKQUOTE>

with

<BLOCKQUOTE>
In an explicit specialization for such a member...
</BLOCKQUOTE>

<P>
<B>Notes from 04/00 meeting:</B>
</P>

<P>This issue was kept in "review" status for two major reasons:</P>

<OL>

<LI>It's not clear that a change is actually needed.  All uses of the
phrase "in the namespace" in the IS mean "directly in the namespace,"
not in a scope nested within the namespace.</LI>

<LI>There was substantial sentiment for actually adding support for
in-class specializations at a future time, and it might be perceived
as a reversal of direction to pass a change aimed at reinforcing the
absence of the feature, only to turn around afterward and add it.</LI>

</OL>

<P>
<B>Notes from 10/00 meeting:</B>
</P>

<P>The core working group felt that the value of additional
clarity here outweighs the potential disadvantages that were noted
at the preceding meeting.</P>

<BR>
<BR>
<HR>
<A NAME="275"></A>
<H4>275.
  
Explicit instantiation/specialization and <I>using-directive</I>s
</H4>
<B>Section: </B>14.7.3&nbsp;



 <A HREF="template.html#temp.expl.spec">temp.expl.spec</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>John Spicer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>15 Feb 2001<BR>


<P>[Moved to DR at 4/02 meeting.]</P>



<P>Consider this example:</P>

<PRE>
    namespace N {
	template &lt;class T&gt; void f(T){}
	template &lt;class T&gt; void g(T){}
	template &lt;&gt; void f(int);
	template &lt;&gt; void f(char);
	template &lt;&gt; void g(char);
    }

    using namespace N;

    namespace M {
	template &lt;&gt; void N::f(char){}  // prohibited by standard
	template &lt;class T&gt; void g(T){}
	template &lt;&gt; void g(char){}     // specialization of M::g or ambiguous?
	template void f(long);         // instantiation of N::f?
    }

    template &lt;class T&gt; void g(T){}

    template &lt;&gt; void N::f(char){}  // okay
    template &lt;&gt; void f(int){}      // is this a valid specialization of N::f?

    template void g(int);          // instantiation of ::g(int) or ambiguous?
</PRE>

<P>The question here is whether unqualified names made visible by a
<I>using-directive</I> can be used as the declarator in an explicit
instantiation or explicit specialization.</P>

<P>Note that this question is already answered for qualified names in
8.3&nbsp;



 <A HREF="decl.html#dcl.meaning">dcl.meaning</A> paragraph 1.  In a qualified name such as
<TT>N::f</TT>, <TT>f</TT> must be a member of class or namespace
<TT>N</TT>, not a name made visible in <TT>N</TT> by a
<I>using-directive</I> (or a <I>using-declaration</I>, for that
matter).</P>

<P>The standard does not, as far as I can tell, specify the behavior of
these cases one way or another.</P>

<P>My opinion is that names from <I>using-directive</I>s should not be
considered when looking up the name in an unqualified declarator in an
explicit specialization or explicit instantiation.  In such cases, it
is reasonable to insist that the programmer know exactly which
template is being specialized or instantiated, and that a qualified
name must be used if the template is a member of a namespace.</P>

<P>As the example illustrates, allowing names from
<I>using-directive</I>s to be used would also have the affect of
making ambiguous otherwise valid instantiation and specialization
directives.</P>

<P>Furthermore, permitting names from <I>using-directive</I>s would
require an additional rule to prohibit the explicit instantiation of
an entity in one namespace from being done in another (non-enclosing)
namespace (as in the instantiation of <TT>f</TT> in namespace
<TT>M</TT> in the example).</P>

<P>
<U>Mike Miller</U>: I believe the explicit specialization case
is already covered by 7.3.1.2&nbsp;



 <A HREF="dcl.html#namespace.memdef">namespace.memdef</A> paragraph 2,
which requires using a qualified name to define a namespace member
outside its namespace.</P>

<P>
<U>John Spicer</U>: 7.3.1.2&nbsp;



 <A HREF="dcl.html#namespace.memdef">namespace.memdef</A> deals with
namespace members.  An explicit specialization directive deals with
something that is a specialization of a namespace member.  I don't
think the rules in 7.3.1.2&nbsp;



 <A HREF="dcl.html#namespace.memdef">namespace.memdef</A> could be taken to
apply to specializations unless the standard said so explicitly.</P>

<P>
<B>Proposed resolution (suggested 04/01, proposed 10/01)</B>:</P>

<P>(The first change below will need to be revised in accordance
with the resolution of <A HREF="
     cwg_defects.html#284">issue 284</A> to
add a cross-reference to the text dealing with class names.)</P>

<OL>

<LI>
<P>Add in 14.7.2&nbsp;



 <A HREF="template.html#temp.explicit">temp.explicit</A> paragraph 2 before the
example:</P>

<BLOCKQUOTE>

An explicit instantiation shall appear in an enclosing namespace
of its template.  If the name declared in the explicit
instantiation is an unqualified name, the explicit instantiation
shall appear in the namespace where its template is declared.
[<I>Note:</I> Regarding qualified names in declarators, see
8.3&nbsp;



 <A HREF="decl.html#dcl.meaning">dcl.meaning</A>.]

</BLOCKQUOTE>

</LI>

<LI>
<P>Change the first sentence of 7.3.1.2&nbsp;



 <A HREF="dcl.html#namespace.memdef">namespace.memdef</A>
paragraph 1 from</P>

<BLOCKQUOTE>

Members of a namespace can be defined within that namespace.

</BLOCKQUOTE>

<P>to</P>

<BLOCKQUOTE>

Members (including explicit specializations of templates
(14.7.3&nbsp;



 <A HREF="template.html#temp.expl.spec">temp.expl.spec</A>)) of a namespace can be defined
within that namespace.

</BLOCKQUOTE>

</LI>

<LI>
<P>Change the first sentence of 7.3.1.2&nbsp;



 <A HREF="dcl.html#namespace.memdef">namespace.memdef</A>
paragraph 2 from</P>

<BLOCKQUOTE>

Members of a named namespace can also be defined...

</BLOCKQUOTE>

<P>to</P>

<BLOCKQUOTE>

Members (including explicit specializations of templates (14.7.3&nbsp;



 <A HREF="template.html#temp.expl.spec">temp.expl.spec</A>)) of a named namespace can also be defined...

</BLOCKQUOTE>

</LI>

<LI>
<P>Change the last sentence of 14.7.3&nbsp;



 <A HREF="template.html#temp.expl.spec">temp.expl.spec</A>
paragraph 2 from</P>

<BLOCKQUOTE>

If the declaration is not a definition, the specialization may be
defined later in the namespace in which the explicit specialization
was declared, or in a namespace that encloses the one in which the
explicit specialization was declared.

</BLOCKQUOTE>

<P>to</P>

<BLOCKQUOTE>

If the declaration is not a definition, the specialization may be
defined later (7.3.1.2&nbsp;



 <A HREF="dcl.html#namespace.memdef">namespace.memdef</A>).

</BLOCKQUOTE>

</LI>

</OL>

<BR>
<BR>
<HR>
<A NAME="336"></A>
<H4>336.
  
Explicit specialization examples are still incorrect
</H4>
<B>Section: </B>14.7.3&nbsp;



 <A HREF="template.html#temp.expl.spec">temp.expl.spec</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Jason Shirk
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>29 Jan 2002<BR>


<P>[Voted into WP at April 2003 meeting.]</P>



<P>The examples corrected by <A HREF="
     cwg_defects.html#24">issue 24</A> are still
wrong in one case.</P>

<P>In item #4 (a correction to the example in paragraph 18), the proposed
resolution is:</P>
<PRE>
  template&lt;class T1&gt; class A { 
    template&lt;class T2&gt; class B { 
      template&lt;class T3&gt; void mf1(T3); 
        void mf2(); 
      }; 
  }; 
  template&lt;&gt; template&lt;class X&gt; 
    class A&lt;int&gt;::B { }; 
  template&lt;&gt; template&lt;&gt; template&lt;class T&gt; 
    void A&lt;int&gt;::B&lt;double&gt;::mf1(T t) { }
  template&lt;class Y&gt; template&lt;&gt; 
    void A&lt;Y&gt;::B&lt;double&gt;::mf2() { } // ill-formed; B&lt;double&gt; is specialized but 
                                    // its enclosing class template A is not 
</PRE>

<P>The explicit specialization of member <TT>A&lt;int&gt;::B&lt;double&gt;::mf1</TT>
is ill-formed.  The class template <TT>A&lt;int&gt;::B</TT>
is explicitly specialized and
contains no members, so any implicit specialization (such as
<TT>A&lt;int&gt;::B&lt;double&gt;</TT>) would also contain no members.</P>

<P>
<B>Proposed Resolution (4/02):</B>
</P>

<P>
Fix the example in 14.7.3&nbsp;



 <A HREF="template.html#temp.expl.spec">temp.expl.spec</A> paragraph 18 to read:</P>
<PRE>
  template&lt;class T1&gt; class A { 
    template&lt;class T2&gt; class B { 
      template&lt;class T3&gt; void mf1(T3);
      void mf2(); 
    }; 
  }; 
  template&lt;&gt; template&lt;class X&gt; 
    class A&lt;int&gt;::B {
      template&lt;class T&gt; void mf1(T);
    }; 
  template&lt;&gt; template&lt;&gt; template&lt;class T&gt; 
    void A&lt;int&gt;::B&lt;double&gt;::mf1(T t) { }
  template&lt;class Y&gt; template&lt;&gt; 
    void A&lt;Y&gt;::B&lt;double&gt;::mf2() { } // ill-formed; B&lt;double&gt; is specialized but 
                                    // its enclosing class template A is not 
</PRE>

<BR>
<BR>
<HR>
<A NAME="337"></A>
<H4>337.
  
Attempt to create array of abtract type should cause deduction to fail
</H4>
<B>Section: </B>14.8.2&nbsp;



 <A HREF="template.html#temp.deduct">temp.deduct</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>John Spicer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>30 Jan 2002<BR>


<P>[Voted into WP at April 2003 meeting.]</P>

<P>In 14.8.2&nbsp;



 <A HREF="template.html#temp.deduct">temp.deduct</A>, attempting to create an array
of abstract class type should
be included in the list of things that cause type deduction to fail.</P>

<P>
<B>Proposed Resolution (4/02):</B>
</P>

<P> In 14.8.2&nbsp;



 <A HREF="template.html#temp.deduct">temp.deduct</A> paragraph 2 amend the bullet item:</P>
<BLOCKQUOTE>
Attempting to create an array with an element type that is <TT>void</TT>,
a function type, or a reference type, or attempting to create an array
with a size that is zero or negative.
</BLOCKQUOTE>

<P> To the following:</P>
<BLOCKQUOTE>
Attempting to create an array with an element type that is <TT>void</TT>,
a function type, <S>or</S> a reference type, <B>or an abstract class
type,</B> or
attempting to create an array with a size that is zero or negative.
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="368"></A>
<H4>368.
  
Uses of non-type parameters that should cause deduction to fail
</H4>
<B>Section: </B>14.8.2&nbsp;



 <A HREF="template.html#temp.deduct">temp.deduct</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Jason Shirk
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>29 July 2002<BR>


<P>[Voted into WP at October 2003 meeting.]</P>

<P>I understand the rules in 14.8.2&nbsp;



 <A HREF="template.html#temp.deduct">temp.deduct</A> paragraph 2
are meant to be an exhaustive list of what can cause type deduction to
fail.</P>

<P>Consider:</P>
<PRE>
  template&lt;typename U,U u&gt; struct wrap_t;

  template&lt;typename U&gt; static yes check( wrap_t&lt;U,U(0)&gt;* );

  struct X { X(int); };
  int main() {
    check&lt;X&gt;(0);
  }
</PRE>
<P>I can see 2 reasons this might cause type deduction to fail:</P>
<UL>
<LI>
Conversion is not a compile time constant.
</LI>
<LI>
Non-type parameter is a class type.
</LI>
</UL>
<P>Neither case is mentioned in 14.8.2&nbsp;



 <A HREF="template.html#temp.deduct">temp.deduct</A> paragraph 2,
nor do I see a DR mentioning these.</P>

<P>
<B>Proposed resolution (October 2002):</B>
</P>

<P>Add after the fourth-to-last bullet of
14.8.2&nbsp;



 <A HREF="template.html#temp.deduct">temp.deduct</A> paragraph 2:</P>
<BLOCKQUOTE>
<UL>
<LI>
Attempting to give an invalid type to a nontype template parameter.
[<I>Example:</I>
<PRE>
  template &lt;class T, T&gt; struct S {};
  template &lt;class T&gt; int f(S&lt;T, T()&gt;*);
  struct X {};
  int i0 = f&lt;X&gt;(0);
</PRE>
]
</LI>
</UL>
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="398"></A>
<H4>398.
  
Ambiguous wording on naming a type in deduction
</H4>
<B>Section: </B>14.8.2&nbsp;



 <A HREF="template.html#temp.deduct">temp.deduct</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Daveed Vandevoorde
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>16 Jan 2003<BR>


<P>[Voted into WP at March 2004 meeting.]</P>



<P>The following example (simplified from a posting to
comp.lang.c++.moderated) is accepted by some
compilers (e.g., EDG), but not by other (e.g., g++).</P>
<PRE>
  struct S {
    static int const I = 42;
  };

  template&lt;int N&gt; struct X {};

  template&lt;typename T&gt; void f(X&lt;T::I&gt;*) {}

  template&lt;typename T&gt; void f(X&lt;T::J&gt;*) {}

  int main() {
    f&lt;S&gt;(0);
  }
</PRE>

<P>The wording in the standard that normally would
cover this (third sub-bullet in 14.8.2&nbsp;



 <A HREF="template.html#temp.deduct">temp.deduct</A>
paragraph 2) says:
<BLOCKQUOTE>
    Attempting to use a type in the qualifier portion of a
    qualified name <B>that names a type</B> when that type does
    not contain the specified member, or if the specified
    member is not a type where a type is required.
</BLOCKQUOTE>
(emphasis mine).  If the phrase "that names a
type" applies to "a qualified name," then the example
is invalid.  If it applies to "the qualifier portion,"
then it is valid (because the second candidate is simply
discarded).</P>

<P>I suspect we want this example to work.  Either way,
I believe the sub-bullet deserves clarification.</P>

<P>
<B>Notes from April 2003 meeting:</B>
</P>

<P>We agreed that the example should be valid.  The phrase "that
names a type" applies to "the qualifier portion."</P>

<P>
<B>Proposed resolution (October 2003):</B>
</P>

<P>
In 14.8.2&nbsp;



 <A HREF="template.html#temp.deduct">temp.deduct</A>, paragraph 2, bullet 3,
sub-bullet 3, replace</P>

<BLOCKQUOTE>
Attempting to use a type in the qualifier portion of a qualified name
that names a type when that type does not contain the
specified member, or if the specified member is not a type
where a type is required.
</BLOCKQUOTE>

<P>
With</P>

<BLOCKQUOTE>
Attempting to use a type
in a <I>nested-name-specifier</I> of a <I>qualified-id</I>
when that type does not contain the specified member, or
<UL>
<LI>
the specified member is not a type where a type is required, or
</LI>
<LI>
the specified member is not a template where a template is required,
or
</LI>
<LI>
the specified member is not a nontype where a nontype is required.
</LI>
</UL>
<P>
[<I>Example:</I>
</P>
</BLOCKQUOTE>

<P>
Replace the example that follows the above text with</P>

<BLOCKQUOTE>
<PRE>
template &lt;int I&gt; struct X { };
template &lt;template &lt;class T&gt; class&gt; struct Z {};
template &lt;class T&gt; void f(typename T::Y*){}
template &lt;class T&gt; void g(X&lt;T::N&gt;*){}
template &lt;class T&gt; void h(Z&lt;T::template TT&gt;*){}
struct A {};
struct B { int Y; };
struct C {
	typedef int N;
};
struct D {
	typedef int TT;
};

int main()
{
	// Deduction fails in each of these cases:
	f&lt;A&gt;(0); // A does not contain a member Y
	f&lt;B&gt;(0); // The Y member of B is not a type
	g&lt;C&gt;(0); // The N member of C is not a nontype
	h&lt;D&gt;(0); // The TT member of D is not a template
}
</PRE>
]
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="486"></A>
<H4>486.
  
Invalid return types and template argument deduction
</H4>
<B>Section: </B>14.8.2&nbsp;



 <A HREF="template.html#temp.deduct">temp.deduct</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>John Spicer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>16 Nov 2004<BR>


<P>[Voted into WP at April, 2006 meeting.]</P>

<P>According to 14.8.2&nbsp;



 <A HREF="template.html#temp.deduct">temp.deduct</A> paragraph 2,</P>

<BLOCKQUOTE>

If a substitution in a template parameter or in the function type
of the function template results in an invalid type, type
deduction fails.

</BLOCKQUOTE>

<P>That would seem to apply to cases like the following:</P>

<PRE>
    template &lt;class T&gt; T f(T&amp;){}
    void f(const int*){}
    int main() {
      int a[5];
      f(a);
    }
</PRE>

<P>Here, the return type of <TT>f</TT> is deduced as
<TT>int[5]</TT>, which is invalid according to 8.3.5&nbsp;



 <A HREF="decl.html#dcl.fct">dcl.fct</A> paragraph 6.  The outcome of this example, then,
should presumably be that type deduction fails and overload
resolution selects the non-template function.  However, the list
of reasons in 14.8.2&nbsp;



 <A HREF="template.html#temp.deduct">temp.deduct</A> for which type
deduction can fail does not include function and array types as a
function return type.  Those cases should be added to the
list.</P>

<P>
<B>Proposed resolution (October, 2005):</B>
</P>

<P>Change the last sub-bullet of 14.8.2&nbsp;



 <A HREF="template.html#temp.deduct">temp.deduct</A>
paragraph 2 as indicated:</P>

<UL>
<LI>
<P>Attempting to create a function type in which a parameter
has a type of <TT>void</TT><B>, or in which the return type is a
function type or array type</B>.</P>
</LI>
</UL>

<BR>
<BR>
<HR>
<A NAME="352"></A>
<H4>352.
  
Nondeduced contexts
</H4>
<B>Section: </B>14.8.2.1&nbsp;



 <A HREF="template.html#temp.deduct.call">temp.deduct.call</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Andrei Iltchenko
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>24 April 2002<BR>


<P>[Voted into WP at March 2004 meeting.]</P>

<P>The current definition of the C++ language speaks about nondeduced
contexts only in terms of deducing template arguments from a type
14.8.2.5&nbsp;



 <A HREF="template.html#temp.deduct.type">temp.deduct.type</A> paragraph 4. Those cases, however, don't
seem to be the only ones when template argument deduction is not
possible. The example below illustrates that:</P>
<PRE>
namespace  A  {
   enum  ae  {   };
   template&lt;class R, class A&gt;
   int  foo(ae, R(*)(A))
   {   return  1;   }
}

template&lt;typename T&gt;
void  tfoo(T)
{   }

template&lt;typename T&gt;
int  tfoo(T)
{   return  1;   }

/*int  tfoo(int)
{   return  1;   }*/


int  main()
{
   A::ae   a;
   foo(a, &amp;tfoo);
}
</PRE>
<P>Here argument-dependent name lookup finds the function template
'A::foo' as a candidate function. None of the function template's
function parameter types constitutes a nondeduced context as per
14.8.2.5&nbsp;



 <A HREF="template.html#temp.deduct.type">temp.deduct.type</A> paragraph 4. And yet, quite clearly,
argument deduction is not possible in this context. Furthermore it is
not clear what a conforming implementation shall do when the
definition of the non-template function '::tfoo' is uncommented.</P>

<P>
<B>Suggested resolution:</B>
</P>

<P>Add the following as a new paragraph immediately before paragraph 3 of
14.8.2.1&nbsp;



 <A HREF="template.html#temp.deduct.call">temp.deduct.call</A>:</P>
<BLOCKQUOTE>
<P>After the above transformations, in the event of P being a function
type, a pointer to function type, or a pointer to member function type
and the corresponding A designating a set of overloaded (member)
functions with at least one of the (member) functions introduced by
the use of a (member) function template name (13.4&nbsp;



 <A HREF="over.html#over.over">over.over</A>)
or by the use of a
conversion function template (14.8.2.3&nbsp;



 <A HREF="template.html#temp.deduct.conv">temp.deduct.conv</A>),
the whole function call
expression is considered to be a nondeduced context. [Example:</P>
<PRE>
namespace  A  {
   enum  ae  {   };
   template&lt;class R, class A&gt;
   int  foo(ae, R(*)(A))
   {   return  1;   }
}

template&lt;typename T&gt;
void  tfoo(T)
{   }

template&lt;typename T&gt;
int  tfoo(T)
{   return  1;   }

int  tfoo(int)
{   return  1;   }

int  main()
{
   A::ae   a;
   foo(a, &amp;tfoo);   //  ill-formed, the call is a nondeduced context
   using  A::foo;
   foo&lt;void,int&gt;(a, &amp;tfoo);  // well-formed, the address of the spe-
                             // cialization 'void tfoo&lt;int&gt;(int)' is
                             // the second argument of the call
}
</PRE>
</BLOCKQUOTE>



<P>
<B>Notes from October 2002 meeting:</B>
</P>

<P>There was agreement that deduction should fail but it's still possible
to get a result -- it's just not a "nondeduced context" in the
sense of the standard.</P>

<P>The presence of a template in the overload set should not automatically
disqualify the overload set.</P>

<P>
<B>Proposed Resolution (April 2003, revised October 2003):</B>
</P>

<P>
In 14.8.2.5&nbsp;



 <A HREF="template.html#temp.deduct.type">temp.deduct.type</A> paragraph 4 replace:
<BLOCKQUOTE>
The nondeduced contexts are:
<UL>
<LI>
The <I>nested-name-specifier</I> of a type that was specified using a
<I>qualified-id</I>.
</LI>
<LI>
A type that is a <I>template-id</I> in which one or more of the
<I>template-argument</I>s is an expression that references a
<I>template-parameter</I>.
</LI>
</UL>
</BLOCKQUOTE>

with:

<BLOCKQUOTE>
The nondeduced contexts are:
<UL>
<LI>
The <I>nested-name-specifier</I> of a type that was specified using a
<I>qualified-id</I>.
</LI>
<LI>
A non-type template argument or an array bound that is an expression
that references a template-parameter.
</LI>
<LI>
A template parameter used in the parameter type of a function parameter
that has a default argument that is being used in the call
for which argument deduction is being done.
</LI>
<LI>
A function parameter for which argument deduction cannot be done
because the associated function argument is a function, or a set of
overloaded functions (13.4&nbsp;



 <A HREF="over.html#over.over">over.over</A>), and one or
more of the following apply:
<UL>
<LI>
more than one function matches the function parameter type
(resulting in an ambiguous deduction), or
</LI>
<LI>
no function matches the function parameter type, or
</LI>
<LI>
the set of functions supplied as an argument contains one or more
function templates.
</LI>
</UL>
</LI>
</UL>
</BLOCKQUOTE>
</P>

<P>
In 14.8.2.1&nbsp;



 <A HREF="template.html#temp.deduct.call">temp.deduct.call</A>, add after paragraph 3:</P>

<BLOCKQUOTE>
<P>When P is a function type, pointer to function type, or pointer to
member function type:</P>

<UL>
<LI>
If the argument is an overload set containing one or more function templates,
the parameter is treated as a nondeduced context.
</LI>
<LI>
If the argument is an overload set (not containing function templates),
trial argument deduction is attempted using each of the members of the set.
If deduction succeeds for only one of the overload set members, that member
is used as the argument value for deduction.  If deduction succeeds for more
than one member of the overload set the parameter is treated as a nondeduced
context.
</LI>
</UL>

<P>
[Example:
<PRE>
// Only one function of an overload set matches the call so the function
// parameter is a deduced context.
template &lt;class T&gt; int f(T (*p)(T));
int g(int);
int g(char);
int i = f(g);  // calls f(int (*)(int))
</PRE>
--end example]</P>

<P>
[Example:
<PRE>
// Ambiguous deduction causes the second function parameter to be a
// nondeduced context.
template &lt;class T&gt; int f(T, T (*p)(T));
int g(int);
char g(char);
int i = f(1, g);  // calls f(int, int (*)(int))
</PRE>
--end example]</P>

<P>
[Example:
<PRE>
// The overload set contains a template, causing the second function
// parameter to be a nondeduced context.
template &lt;class T&gt; int f(T, T (*p)(T));
char g(char);
template &lt;class T&gt; T g(T);
int i = f(1, g);  // calls f(int, int (*)(int))
</PRE>
--end example]</P>


</BLOCKQUOTE>

<P>
In 14.8.2.5&nbsp;



 <A HREF="template.html#temp.deduct.type">temp.deduct.type</A> paragraph 14, replace:

<BLOCKQUOTE>
If, in the declaration of a function template with a non-type
<I>template-parameter</I>, the non-type <I>template-parameter</I> is
used in an expression in the function parameter-list, the
corresponding <I>template-argument</I> must always be explicitly
specified or deduced elsewhere because type deduction would otherwise
always fail for such a <I>template-argument</I>.
</BLOCKQUOTE>

With:

<BLOCKQUOTE>
If, in the declaration of a function template with a non-type
template parameter, the non-type template parameter is
used in an expression in the function parameter list, the
expression is a nondeduced context.
</BLOCKQUOTE>
</P>

<P>
Replace the example with:</P>

<BLOCKQUOTE>
[Example:
<PRE>
template&lt;int i&gt; class A { /* ... */ };
template&lt;int i&gt; void g(A&lt;i+1&gt;);
template&lt;int i&gt; void f(A&lt;i&gt;, A&lt;i+1&gt;);
void k() {
  A&lt;1&gt; a1;
  A&lt;2&gt; a2;
  g(a1);  //error: deduction fails for expression i+1
  g&lt;0&gt;(a1); //OK
  f(a1, a2);  // OK
}
</PRE>
--end example]
</BLOCKQUOTE>


<P>
In 14.8.2.5&nbsp;



 <A HREF="template.html#temp.deduct.type">temp.deduct.type</A> paragraph 16, replace:</P>

<BLOCKQUOTE>
A <I>template-argument</I> can be deduced from a pointer to function
or pointer to member function argument if the set of overloaded
functions does not contain function templates and at most
one of a set of overloaded functions provides a unique match.
</BLOCKQUOTE>

<P>
With:</P>

<BLOCKQUOTE>
A <I>template-argument</I> can be deduced from a function,
pointer to function, or pointer to member function type.
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="322"></A>
<H4>322.
  
Deduction of reference conversions
</H4>
<B>Section: </B>14.8.2.3&nbsp;



 <A HREF="template.html#temp.deduct.conv">temp.deduct.conv</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Jason Merrill
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>14 Nov 2001<BR>


<P>[Voted into WP at April 2003 meeting.]</P>



<P>Consider:
<PRE>
  struct S {
    template &lt;class T&gt; operator T&amp; ();
  };

  int main ()
  {
    S s;
    int i = static_cast&lt;int&amp;&gt; (s);
  }
</PRE>
14.8.2.3&nbsp;



 <A HREF="template.html#temp.deduct.conv">temp.deduct.conv</A> says that we strip the
reference from <TT>int&amp;</TT>, but doesn't say
anything about <TT>T&amp;</TT>.  As a result, <TT>P</TT> (<TT>T&amp;</TT>)
and <TT>A</TT> (<TT>int</TT>) have incompatible forms
and deduction fails.</P>

<P>
<B>Proposed Resolution (4/02):</B>
</P>

<P>Change the last chunk of 14.8.2.3&nbsp;



 <A HREF="template.html#temp.deduct.conv">temp.deduct.conv</A> paragraph 2 from
<BLOCKQUOTE>
     If <TT>A</TT> is a cv-qualified type, the top level cv-qualifiers
     of <TT>A</TT>'s type are ignored for type deduction.  If
     <TT>A</TT> is a reference type, the type referred to by
     <TT>A</TT> is used for type deduction.
</BLOCKQUOTE>
to
<BLOCKQUOTE>
     If <TT>A</TT> is a cv-qualified type, the top level cv-qualifiers
     of <TT>A</TT>'s type are ignored for type deduction.  If <TT>A</TT> is a
     reference type, the type referred to by <TT>A</TT> is used for
     type deduction.  If <TT>P</TT> is a reference type, the type
     referred to by <TT>P</TT> is used for type deduction.
</BLOCKQUOTE>
</P>

<BR>
<BR>
<HR>
<A NAME="349"></A>
<H4>349.
  
Template argument deduction for conversion functions and qualification conversions
</H4>
<B>Section: </B>14.8.2.3&nbsp;



 <A HREF="template.html#temp.deduct.conv">temp.deduct.conv</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>John Spicer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>16 April 2002<BR>


<P>[Voted into WP at October 2003 meeting.]</P>



<P>We ran into an issue concerning qualification conversions when doing
template argument deduction for conversion functions.</P>

<P>The question is: What is the type of T in the conversion functions
called by this example?  Is T "int" or "const int"?</P>

<P>If T is "int", the conversion function in class A works and the one in
class B fails (because the return expression cannot be converted to
the return type of the function).  If T is "const int", A fails and B
works.</P>

<P>Because the qualification conversion is performed on the result of the
conversion function, I see no benefit in deducing T as const int.</P>

<P>In addition, I think the code in class A is more likely to occur than
the code in class B.  If the author of the class was planning on returning
a pointer to a const entity, I would expect the function to have been
written with a const in the return type.</P>

<P>Consequently, I believe the correct result should be that T is int.</P>
<PRE>
struct A {
	template &lt;class T&gt; operator T***() {
		int*** p = 0;
		return p;
	}
};

struct B {
	template &lt;class T&gt; operator T***() {
		const int*** p = 0;
		return p;
	}
};

int main()
{
	A a;
	const int * const * const * p1 = a;
	B b;
	const int * const * const * p2 = b;
}
</PRE>
<P>We have just implemented this feature, and pending clarification by
the committee, we deduce T as int.  It appears that g++ and the Sun
compiler deduce T as const int.</P>

<P>One way or the other, I think the standard should be clarified to
specify how cases like this should be handled.</P>

<P>
<B>Notes from October 2002 meeting:</B>
</P>

<P>There was consensus on having the deduced type be "int" in the
above.</P>

<P>
<B>Proposed resolution (April 2003):</B>
</P>

<P>
Add to the end of 14.8.2.3&nbsp;



 <A HREF="template.html#temp.deduct.conv">temp.deduct.conv</A> (as a new paragraph
following paragraph 3):</P>
<BLOCKQUOTE>
<P>When the deduction process requires a qualification conversion for a
pointer or pointer to member type as described above, the following
process is used to determine the deduced template argument values:</P>

<P> If <TT>A</TT> is a type <I>cv</I><SUB>1,0</SUB> pointer to ... <I>cv</I>
<SUB>1,<I>n</I>-1</SUB>
pointer to <I>cv</I><SUB>1,<I>n</I></SUB> <I>T1</I>
</P>
<P> and <TT>P</TT> is a type <I>cv</I><SUB>2,0</SUB>
pointer to ... <I>cv</I><SUB>2,<I>n</I>-1</SUB>
pointer to <I>cv</I><SUB>2,<I>n</I></SUB> <I>T2</I>
</P>
<P> The cv-unqualified T1 and T2 are used as the types of
<TT>A</TT> and <TT>P</TT> respectively for type deduction.</P>

<P>
[<I>Example:</I>
<PRE>
struct A {
	template &lt;class T&gt; operator T***();
};

A a;
const int * const * const * p1 = a;  // T is deduced as int, not const int
</PRE>
-- <I>end example</I>]
</P>
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="70"></A>
<H4>70.
  
Is an array bound a nondeduced context?
</H4>
<B>Section: </B>14.8.2.5&nbsp;



 <A HREF="template.html#temp.deduct.type">temp.deduct.type</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Jack Rouse
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>29 Sep 1998<BR>



<P>[Moved to DR at 4/01 meeting.]</P>

<P>Paragraph 4 lists contexts in which template formals are not deduced.
Were template formals in an expression in the array bound of an array type
specification intentionally left out of this list? Or was the intent
that such formals always be explicitly specified? Otherwise I believe the
following should be valid:</P>
<PRE>
    template &lt;int I&gt; class IntArr {};

    template &lt;int I, int J&gt;
    void concat( int (&amp;d)[I+J], const IntArr&lt;I&gt;&amp; a, const IntArr&lt;J&gt;&amp; b ) {}

    int testing()
    {
        IntArr&lt;2&gt; a;
        IntArr&lt;3&gt; b;
        int d[5];

        concat( d, a, b );
    }
</PRE>
Can anybody shed some light on this?

<P>
<U>From John Spicer:</U>
</P>

<P>Expressions involving nontype template parameters are nondeduced
contexts, even though they are omitted from the list in
14.8.2.5&nbsp;



 <A HREF="template.html#temp.deduct.type">temp.deduct.type</A>
 paragraph 4. See
14.8.2.5&nbsp;



 <A HREF="template.html#temp.deduct.type">temp.deduct.type</A>
 paragraphs
12-14:</P>

<OL START="12">
<LI>
A template type argument cannot be deduced from the type of a non-type
<I>template-argument</I>.
<P>&nbsp;...</P>
</LI>
</OL>
<OL START="14">
<LI>
If, in the declaration of a function template with
a non-type <I>template-parameter</I>, the non-type <I>template-parameter</I>
is used in an expression in the function parameter-list, the corresponding
<I>template-argument</I> must always be explicitly specified or deduced
elsewhere because type deduction would otherwise always
fail for such a <I>template-argument</I>.</LI>
</OL>

<P>
<B>Proposed resolution (04/01):</B> In
14.8.2.5&nbsp;



 <A HREF="template.html#temp.deduct.type">temp.deduct.type</A>
 paragraph 4, add a
third bullet:</P>

<UL>
<LI>
An array bound that is an expression that references a
<I>template-parameter</I>
</LI>
</UL>
<BR>
<BR>
<HR>
<A NAME="300"></A>
<H4>300.
  
References to functions in template argument deduction
</H4>
<B>Section: </B>14.8.2.5&nbsp;



 <A HREF="template.html#temp.deduct.type">temp.deduct.type</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Andrei Iltchenko
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>11 Jul 2001<BR>


<P>[Moved to DR at October 2002 meeting.]</P>

<P>Paragraph 9 of 14.8.2.5&nbsp;



 <A HREF="template.html#temp.deduct.type">temp.deduct.type</A> enumerates the
forms that the types P and A need to have in order for template
argument deduction to succeed.</P>

<P>For P denoting a pointer to function the paragraph lists the following
forms as allowing for template argument deduction:</P>
<PRE>
type(*)(T)
T(*)()
T(*)(T)
</PRE>

<P>On the other hand, no provision has been made to accommodate similar
cases for references to functions, which in light of the wording of
14.8.2.5&nbsp;



 <A HREF="template.html#temp.deduct.type">temp.deduct.type</A> paragraph 11 means that the program below
is ill-formed (some of the C++ compilers do not reject it however):</P>

<PRE>
    template&lt;typename Arg, typename Result, typename T&gt;
    Result  foo_r(Result(&amp; rf)(Arg), T x)
    {   return  rf(Arg(x));   }

    template&lt;typename Arg, typename Result, typename T&gt;
    Result  foo_p(Result(* pf)(Arg), T x)
    {   return  pf(Arg(x));   }

    #include &lt;iostream&gt;
    int  show_arg(char c)
    {
       std::cout &lt;&lt; c &lt;&lt; ' ';
       if(std::cout)  return  0;
       return  -1;
    }

    int  main()
    {
                                                   // The deduction 
       int  (&amp; rf1)(int(&amp;)(char), double) = foo_r; // shall fail here
                                                   // While here
       int  (&amp; rf2)(int(*)(char), double) = foo_p; // it shall succeed
       return  rf2(show_arg, 2);
    }
</PRE>

<P>
<B>Proposed resolution (10/01, same as suggested resolution):</B>
</P>

<P>In the list of allowable forms for the types <TT>P</TT> and
<TT>A</TT> in paragraph 9 of
14.8.2.5&nbsp;



 <A HREF="template.html#temp.deduct.type">temp.deduct.type</A> replace</P>
<PRE>
type(*)(T)
T(*)()
T(*)(T)
</PRE>
<P>by</P>
<PRE>
type(T)
T()
T(T)
</PRE>

<BR>
<BR>
<HR>
<A NAME="208"></A>
<H4>208.
  
Rethrowing exceptions in nested handlers
</H4>
<B>Section: </B>15.1&nbsp;



 <A HREF="except.html#except.throw">except.throw</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Bill Wade
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>28 Feb 2000<BR>



<P>[Moved to DR at 4/01 meeting.]</P>

<P>Paragraph 7 of 15.1&nbsp;



 <A HREF="except.html#except.throw">except.throw</A> discusses which exception
is thrown by a <I>throw-expression</I> with no operand.</P>

<P>May an expression which has been "finished" (paragraph 7) by an
inner catch block be rethrown by an outer catch block?</P>

<PRE>
    catch(...)    // Catch the original exception
    {
      try{ throw; }    // rethrow it at an inner level
                       // (in reality this is probably
                       // inside a function)
      catch (...)
      {
      }   // Here, an exception (the original object)
          // is "finished" according to 15.1p7 wording

      // 15.1p7 says that only an unfinished exception
      // may be rethrown.
      throw;    // Can we throw it again anyway?  It is
                // certainly still alive (15.1p4).
    }
</PRE>

<P>I believe this is ok, since the paragraph says that the exception
is finished when the "corresponding" catch clause exits.  However
since we have two clauses, and only one exception, it would seem that
the one exception gets "finished" twice.</P>

<P>
<B>Proposed resolution (04/01):</B>
</P>

<OL>
<LI>
<P>In 15.1&nbsp;



 <A HREF="except.html#except.throw">except.throw</A> paragraph 4, change

<BLOCKQUOTE>

When the last handler being executed for the exception exits by any
means other than <TT>throw;</TT> ...

</BLOCKQUOTE>

to

<BLOCKQUOTE>

When the last remaining active handler for the exception exits by any
means other than <TT>throw;</TT> ...

</BLOCKQUOTE>
</P>
</LI>

<LI>
<P>In 15.1&nbsp;



 <A HREF="except.html#except.throw">except.throw</A> paragraph 6, change

<BLOCKQUOTE>

A <I>throw-expression</I> with no operand rethrows the exception being
handled.

</BLOCKQUOTE>

to

<BLOCKQUOTE>

A <I>throw-expression</I> with no operand rethrows the currently
handled exception (15.3&nbsp;



 <A HREF="except.html#except.handle">except.handle</A>).

</BLOCKQUOTE>
</P>
</LI>

<LI>
<P>Delete 15.1&nbsp;



 <A HREF="except.html#except.throw">except.throw</A> paragraph 7.</P>
</LI>

<LI>
<P>Add the following before 15.1&nbsp;



 <A HREF="except.html#except.throw">except.throw</A> paragraph
6:

<BLOCKQUOTE>

An exception is considered caught when a handler for that exception
becomes active (15.3&nbsp;



 <A HREF="except.html#except.handle">except.handle</A>).  [<I>Note:</I> an
exception can have active handlers and still be considered uncaught if
it is rethrown.]

</BLOCKQUOTE>
</P>
</LI>

<LI>
<P>Change 15.3&nbsp;



 <A HREF="except.html#except.handle">except.handle</A> paragraph 8 from

<BLOCKQUOTE>

An exception is considered handled upon entry to a handler.
[<I>Note:</I> the stack will have been unwound at that point.]

</BLOCKQUOTE>

to

<BLOCKQUOTE>

<P>A handler is considered active when initialization is complete for
the formal parameter (if any) of the catch clause.  [<I>Note:</I> the
stack will have been unwound at that point.]  Also, an implicit
handler is considered active when <TT>std::terminate()</TT> or
<TT>std::unexpected()</TT> is entered due to a throw.  A handler is no
longer considered active when the catch clause exits or when
<TT>std::unexpected()</TT> exits after being entered due to a throw.</P>

<P>The exception with the most recently activated handler that is
still active is called the <I>currently handled exception</I>.</P>

</BLOCKQUOTE>
</P>
</LI>

<LI>
<P>In 15.3&nbsp;



 <A HREF="except.html#except.handle">except.handle</A> paragraph 16, change "exception
being handled" to "currently handled exception."
</P>
</LI>
</OL>

<BR>
<BR>
<HR>
<A NAME="428"></A>
<H4>428.
  
Mention of expression with reference type
</H4>
<B>Section: </B>15.1&nbsp;



 <A HREF="except.html#except.throw">except.throw</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Adamczyk
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>14 July 2003<BR>


<P>[Voted into WP at March 2004 meeting.]</P>

<P>15.1&nbsp;



 <A HREF="except.html#except.throw">except.throw</A> paragraph 3 says that the type of a throw
expression shall not be
a pointer or reference to an incomplete type.  But an expression never
has reference type.</P>

<P>
<B>Proposed Resolution (October 2003):</B>
</P>

<P>Change the penultimate sentence of 15.1&nbsp;



 <A HREF="except.html#except.throw">except.throw</A>
 paragraph 3 as follows:</P>
<BLOCKQUOTE>
The type of the <I>throw-expression</I> shall not be an
incomplete type, or a pointer <S>or reference</S>
to an incomplete type <b>other than (possibly cv-qualified)
<TT>void</TT></b><S>, other than <TT>void*</TT>,
<TT>const void*</TT>, <TT>volatile void*</TT>, or
<TT>const volatile void*</TT></S>.
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="479"></A>
<H4>479.
  
Copy elision in exception handling
</H4>
<B>Section: </B>15.1&nbsp;



 <A HREF="except.html#except.throw">except.throw</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>07 Oct 2004<BR>


<P>[Voted into WP at April, 2006 meeting.]</P>



<P>I have noticed a couple of confusing and overlapping passages
dealing with copy elision.  The first is 15.1&nbsp;



 <A HREF="except.html#except.throw">except.throw</A> paragraph 5:</P>

<BLOCKQUOTE>

If the use of the temporary object can be eliminated without
changing the meaning of the program except for the execution of
constructors and destructors associated with the use of the
temporary object (12.2&nbsp;



 <A HREF="special.html#class.temporary">class.temporary</A>), then the exception
in the handler can be initialized directly with the argument of
the throw expression.

</BLOCKQUOTE>

<P>The other is 15.3&nbsp;



 <A HREF="except.html#except.handle">except.handle</A> paragraph 17:</P>

<BLOCKQUOTE>

If the use of a temporary object can be eliminated without
changing the meaning of the program except for execution of
constructors and destructors associated with the use of the
temporary object, then the optional name can be bound directly to
the temporary object specified in a <I>throw-expression</I>
causing the handler to be executed.

</BLOCKQUOTE>

<P>I <I>think</I> these two passages are intended to describe the
same optimization.  However, as is often the case where something
is described twice, there are significant differences.  One is
just different terminology &mdash; is &ldquo;the exception in the
handler&rdquo; the same as &ldquo;the object declared in the
<I>exception-declaration</I> or, if the
<I>exception-declaration</I> does not specify a name, a temporary
object of that type&rdquo; (15.3&nbsp;



 <A HREF="except.html#except.handle">except.handle</A> paragraph
16)?</P>

<P>More significant, there is a difference in which kinds of
<I>throw-expression</I>s are eligible for the optimization.  In
15.1&nbsp;



 <A HREF="except.html#except.throw">except.throw</A> paragraph 5, it appears that any
object is a candidate, while in 15.3&nbsp;



 <A HREF="except.html#except.handle">except.handle</A>
paragraph 17 the thrown object must be
a temporary (&ldquo;the temporary object specified in a
<I>throw-expression</I>&rdquo;).  For example, it's not clear
looking at these two passages whether the copy of a local
automatic can be elided.  I.e., by analogy with the return value
optimization described in 12.8&nbsp;



 <A HREF="special.html#class.copy">class.copy</A> paragraph
15:</P>

<PRE>
    X x;
    return x;    // copy may be elided

    X x;
    throw x;     // unclear whether copy may be elided
</PRE>

<P>Which brings up another point: 12.8&nbsp;



 <A HREF="special.html#class.copy">class.copy</A>
paragraph 15 purports to be an exhaustive list in which copy
elision is permitted even if the constructor and/or destructor
have side effects; however, these two passages describe another
case that is not mentioned in 12.8&nbsp;



 <A HREF="special.html#class.copy">class.copy</A>
paragraph 15.</P>

<P>A final point of confusion: in the unoptimized abstract
machine, there are actually <I>two</I> copies in throwing and
handling an exception: the copy from the object being thrown to
the exception object, and the copy from the exception object to
the object or temporary in the <I>exception-declaration</I>.
15.1&nbsp;



 <A HREF="except.html#except.throw">except.throw</A> paragraph 5 speaks only of eliminating
the exception object, copying the thrown object directly into the
<I>exception-declaration</I> object, while 15.3&nbsp;



 <A HREF="except.html#except.handle">except.handle</A> paragraph 17 refers to directly binding the
<I>exception-declaration</I> object to the thrown object (if it's
a temporary).  Shouldn't these be separated, with a throw of an
automatic object or temporary being like the return value
optimization and the initialization of the object/temporary in
the <I>exception-declaration</I> being a separate optimizable
step (which could, presumably, be combined to effectively alias
the <I>exception-declaration</I> onto the thrown object)?</P>

<P>(See paper J16/04-0165 = WG21 N1725.)</P>

<P>
<B>Proposed resolution (April, 2005):</B>
</P>

<OL>
<LI>
<P>Add two items to the bulleted list in 12.8&nbsp;



 <A HREF="special.html#class.copy">class.copy</A>
paragraph 15 as follows: </P>

<BLOCKQUOTE>

<P>This elision of copy operations is permitted in the following
circumstances (which may be combined to eliminate multiple copies):</P>

<UL>

<LI>
<P>in a <TT>return</TT> statement in a function with a class return type,
when the expression is the name of a non-volatile automatic object
with the same cv-unqualified type as the function return type, the
copy operation can be omitted by constructing the automatic object
directly into the function&rsquo;s return value</P>
</LI>

<B>
<LI>
<P>in a <I>throw-expression</I>, when the operand is the name
of a non-volatile automatic object, the copy operation from the
operand to the exception object (15.1&nbsp;



 <A HREF="except.html#except.throw">except.throw</A>) can be
omitted by constructing the automatic object directly into the
exception object</P>
</LI>
</B>

<LI>
<P>when a temporary class object that has not been bound to a
reference (12.2&nbsp;



 <A HREF="special.html#class.temporary">class.temporary</A>) would be copied to a class
object with the same cv-unqualified type, the copy operation can be
omitted by constructing the temporary object directly into the target
of the omitted copy</P>
</LI>

<B>
<LI>
<P>when the <I>exception-declaration</I> of an exception
handler (clause 15&nbsp;



 <A HREF="except.html#except">except</A>) declares an object of the
same type (except for cv-qualification) as the exception object
(15.1&nbsp;



 <A HREF="except.html#except.throw">except.throw</A>), the copy operation can be omitted by
treating the <I>exception-declaration</I> as an alias for the
exception object if the meaning of the program will be unchanged
except for the execution of constructors and destructors for the
object declared by the <I>exception-declaration</I>
</P>
</LI>
</B>

</UL>

</BLOCKQUOTE>

</LI>

<LI>
<P>Change 15.1&nbsp;



 <A HREF="except.html#except.throw">except.throw</A> paragraph 5 as follows:</P>

<BLOCKQUOTE>

<S>If the use of the temporary object can be eliminated without
changing the meaning of the program except for the execution of
constructors and destructors associated with the use of the temporary
object (12.2&nbsp;



 <A HREF="special.html#class.temporary">class.temporary</A>), then the exception in the handler
can be initialized directly with the argument of the throw
expression.</S> When the thrown object is a class object, <S>and</S>
the copy constructor <S>used to initialize the temporary copy is not</S>
<B>and the destructor shall be</B> accessible, <S>the program is
ill-formed (even when the temporary object could otherwise be
eliminated)</S> <B>even if the copy operation is elided (12.8&nbsp;



 <A HREF="special.html#class.copy">class.copy</A>)</B>. <S>Similarly, if the destructor for that object is
not accessible, the program is ill-formed (even when the temporary
object could otherwise be eliminated).</S>

</BLOCKQUOTE>

</LI>

<LI>
<P>Change 15.3&nbsp;



 <A HREF="except.html#except.handle">except.handle</A> paragraph 17 as follows:</P>

<BLOCKQUOTE>

<S>If the use of a temporary object can be eliminated without changing
the meaning of the program except for execution of constructors and
destructors associated with the use of the temporary object, then the
optional name can be bound directly to the temporary object specified
in a <I>throw-expression</I> causing the handler to be executed.</S>  The
copy constructor and destructor associated with the object shall be
accessible even <S>when the temporary object is eliminated</S>
<B>if the copy operation is elided (12.8&nbsp;



 <A HREF="special.html#class.copy">class.copy</A>)</B>.

</BLOCKQUOTE>

</LI>

</OL>

<BR>
<BR>
<HR>
<A NAME="87"></A>
<H4>87.
  
Exception specifications on function parameters
</H4>
<B>Section: </B>15.4&nbsp;



 <A HREF="except.html#except.spec">except.spec</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Adamczyk
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>25 Jan 1999<BR>



<P>[Moved to DR at 4/01 meeting.]</P>

<P>In
15.4&nbsp;



 <A HREF="except.html#except.spec">except.spec</A>

paragraph 2:</P>
<BLOCKQUOTE>An exception-specification shall appear only on a function
declarator in a function, pointer, reference or pointer to member declaration
or definition.</BLOCKQUOTE>
Does that mean in the top-level function declarator, or one at any level?
Can one, for example, specify an exception specification on a pointer-to-function
parameter of a function?
<PRE>
    void f(int (*pf)(float) throw(A))
</PRE>
Suggested answer: no. The exception specifications are valid only on the
top-level function declarators.
    
<P>However, if exception specifications are made part of a function's type
as has been tentatively agreed, they would have to be allowed on any function
declaration. </P>

<P>There is already an example
of an exception specification for a parameter in the example in
15.4&nbsp;



 <A HREF="except.html#except.spec">except.spec</A>
 paragraph 1.</P>

<P>
<B>Proposed resolution (04/01):</B>

Change text in 15.4&nbsp;



 <A HREF="except.html#except.spec">except.spec</A> paragraph 1 from:</P>

<BLOCKQUOTE>An <I>exception-specification</I> shall appear only on
a function declarator in a function, pointer, reference or pointer to member
declaration or definition.</BLOCKQUOTE>
to:
<BLOCKQUOTE>

An <I>exception-specification</I> shall appear only on a function
declarator for a function type, pointer to function type, reference to
function type, or pointer to member function type that is the
top-level type of a declaration or definition, or on such a type
appearing as a parameter or return type in a function declarator.

</BLOCKQUOTE>
<P>(See also issues <A HREF="
     cwg_defects.html#25">25</A>,
<A HREF="
     cwg_active.html#92">92</A>, and
<A HREF="
     cwg_closed.html#133">133</A>.)</P>
<BR>
<BR>
<HR>
<A NAME="394"></A>
<H4>394.
  
<I>identifier-list</I> is never defined
</H4>
<B>Section: </B>16&nbsp;



 <A HREF="cpp.html#cpp">cpp</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Nicola Musatti
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>16 Dec 2002<BR>


<P>[Voted into WP at October 2004 meeting.]</P>

<P>In clause 16&nbsp;



 <A HREF="cpp.html#cpp">cpp</A>, paragraph 1, the
<I>control-line</I> non-terminal symbol
is defined in terms of the <I>identifier-list</I> non-terminal, which is
never defined within the standard document.</P>

<P>The same definition is repeated in clause A.14&nbsp;



 <A HREF="gram.html#gram.cpp">gram.cpp</A>.</P>

<P>I suggest that the following definition is added to clause
16&nbsp;



 <A HREF="cpp.html#cpp">cpp</A>, paragraph 1, after the one for
<I>replacement-list</I>:</P>
<UL>
<I>identifier-list</I>:
<UL>
<I>identifier</I>
<BR>
<I>identifier-list</I> , <I>identifier</I>
</UL>
</UL>

<P>This should be repeated again in clause A.14&nbsp;



 <A HREF="gram.html#gram.cpp">gram.cpp</A>,
again after the one for <I>replacement-list</I>. It might also be
desirable to include a third repetition in clause 16.3&nbsp;



 <A HREF="cpp.html#cpp.replace">cpp.replace</A>,
paragraph 9.</P>

<P>
<B>Proposed Resolution (Clark Nelson, Dec 2003):</B>
</P>

<P>In clause 16&nbsp;



 <A HREF="cpp.html#cpp">cpp</A>, paragraph 1, immediately
before the definition of <I>replacement-list</I>, add:</P>
<UL>
<I>identifier-list</I>:
<UL>
<I>identifier</I>
<BR>
<I>identifier-list</I> , <I>identifier</I>
</UL>
</UL>

<P>If the correct TROFF macros are used, the definition will appear
automatically in appendix A. It doesn't need to be repeated in 16.3p9.</P>

<P>With respect to the question of having the preprocessor description be
synchronized with C99, this would fall into the category of a justified
difference. (Other justified differences include those for Boolean
expressions, alternative tokens, and terminology differences.)</P>

<BR>
<BR>
<HR>
<A NAME="106"></A>
<H4>106.
  
Creating references to references during template deduction/instantiation
</H4>
<B>Section: </B>unknown&nbsp;



 <A HREF=".html#unknown">unknown</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>WP
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Bjarne Stroustrup
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>unknown<BR>



<P>[Moved to DR at 10/01 meeting.]</P>

<P>The main defect is in the library, where the binder template can
easily lead to reference-to-reference situations.</P>

<P>
<B>Proposed resolution (04/01):</B>
</P>

<OL>

<LI>
Add the following as paragraph 6 of 7.1.3&nbsp;



 <A HREF="dcl.html#dcl.typedef">dcl.typedef</A>:

<BLOCKQUOTE>

<P>If a typedef <TT>TD</TT> names a type "reference to
<I>cv1</I> <TT>S</TT>," an attempt to create the type
"reference to <I>cv2</I> <TT>TD</TT>" creates the type
"reference to <I>cv12"</I> <TT>S</TT>," where <I>cv12</I> is the
union of the cv-qualifiers <I>cv1</I> and <I>cv2</I>.
Redundant qualifiers are ignored.  [<I>Example:</I>
</P>

<PRE>
    int i;
    typedef int&amp; RI;
    RI&amp; r = i;          // r <I>has the type</I> int&amp;
    const RI&amp; r = i;    // r <I>has the type</I> const int&amp;
</PRE>

&mdash;<I>end example</I>]
</BLOCKQUOTE>
</LI>

<LI>
Add the following as paragraph 4 of 14.3.1&nbsp;



 <A HREF="template.html#temp.arg.type">temp.arg.type</A>:

<BLOCKQUOTE>

<P>If a <I>template-argument</I> for a <I>template-parameter</I>
<TT>T</TT> names a type "reference to <I>cv1</I> <TT>S</TT>,"
an attempt to create the type "reference to <I>cv2</I> <TT>T</TT>"
creates the type "reference to <I>cv12</I> <TT>S</TT>," where
<I>cv12</I> is the union of the cv-qualifiers <I>cv1</I> and
<I>cv2</I>.  Redundant cv-qualifiers are ignored.
[<I>Example:</I>
</P>

<PRE>
    template &lt;class T&gt; class X {
        f(const T&amp;);
        /* ... */
    };
    X&lt;int&amp;&gt; x;    // X&lt;int&amp;&gt;::f <I>has the parameter type</I> const int&amp;
</PRE>

&mdash;<I>end example</I>]

</BLOCKQUOTE>
</LI>

<LI>In 14.8.2&nbsp;



 <A HREF="template.html#temp.deduct">temp.deduct</A> paragraph 2 bullet 3 sub-bullet
5, remove the indicated text:

<BLOCKQUOTE>

Attempting to create <S>a reference to a reference type or</S> a
reference to <TT>void</TT>.

</BLOCKQUOTE>
</LI>
</OL>

<P>(See also paper J16/00-0022 = WG21 N1245.)</P>

<BR>
<BR>
<BR>
<BR>
<HR>
<A NAME="TC1 Status"></A>
<H3>Issues with "TC1" Status</H3>
<HR>
<A NAME="173"></A>
<H4>173.
  
Constraints on execution character set
</H4>
<B>Section: </B>2.2&nbsp;



 <A HREF="lex.html#lex.charset">lex.charset</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Markus Mauhart
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>27 Sep 1999<BR>



<P>22.2.1.1.2&nbsp;



 <A HREF="lib-locales.html#lib.locale.ctype.virtuals">lib.locale.ctype.virtuals</A>

paragraph 13 states a constraint on the values of the characters
representing the decimal digits in the execution character set:</P>

<BLOCKQUOTE>
for any digit character <TT>c</TT>, the expression
<TT>(do_narrow( c, dfault)-'0')</TT> evaluates to the digit
value of the character.
</BLOCKQUOTE>

This requirement is not reflected in the description of the
execution character set
(2.2&nbsp;



 <A HREF="lex.html#lex.charset">lex.charset</A>
 paragraph 3).

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>In 2.2&nbsp;



 <A HREF="lex.html#lex.charset">lex.charset</A>
 paragraph 3,
after the sentence</P>

<BLOCKQUOTE>
For each basic execution character
set, the values of the members shall be non-negative and distinct
from one another.
</BLOCKQUOTE>

insert the following:

<BLOCKQUOTE>
In both the source and execution basic character sets, the value of each
character after 0 in the above list of decimal digits shall be one
greater than the value of the previous.
</BLOCKQUOTE>
<BR>
<BR>
<HR>
<A NAME="41"></A>
<H4>41.
  
Clarification of lookup of names after declarator-id
</H4>
<B>Section: </B>3.4.1&nbsp;



 <A HREF="basic.html#basic.lookup.unqual">basic.lookup.unqual</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>1 Sep 1998<BR>





<P>Footnotes 26 and 29 both use the phrase "following the function declarator"
incorrectly: the function declarator includes the parameter list, but the
footnotes make clear that they intend what's said to apply to names inside
the parameter list. Presumably the phrase should be "following the function
<I>declarator-id</I>."</P>

<P>
<B>Proposed Resolution (04/99):</B>
Change the text in 3.4.1&nbsp;



 <A HREF="basic.html#basic.lookup.unqual">basic.lookup.unqual</A>
 
paragraph 6 from:</P>
<BLOCKQUOTE>A name used in the definition of a function [<I>footnote:</I> This
refers to unqualified names following the function declarator; such a name
may be used as a type or as a default argument name in the
<I>parameter-declaration-clause</I>,
or may be used in the function body. <I>end footnote</I>] that is ...</BLOCKQUOTE>
to:
<BLOCKQUOTE>A name used in the definition of a function following the function's
<I>declarator-id [footnote:</I>
This refers to unqualified names that occur, for instance, in a type or
default argument expression in the <I>parameter-declaration-clause</I>
or used in the function body. <I>end footnote</I>] that is ...</BLOCKQUOTE>
Change the text in 3.4.1&nbsp;



 <A HREF="basic.html#basic.lookup.unqual">basic.lookup.unqual</A>
paragraph 8 from:
<BLOCKQUOTE>A name used in the definition of a function that is a member
function (9.3&nbsp;



 <A HREF="class.html#class.mfct">class.mfct</A>
)
[<I>footnote:</I> That is, an unqualified name following the function
declarator; such a name may be used as a type or as a default argument
name in the <I>parameter-declaration-clause</I>, or may be used in the function
body, or, if the function is a constructor, may be used in the expression
of a <I>mem-initializer</I>. <I>end footnote</I>] of class <TT>X</TT> shall be ...</BLOCKQUOTE>
to:
<BLOCKQUOTE>A name used in the definition of a member function
(9.3&nbsp;



 <A HREF="class.html#class.mfct">class.mfct</A>
) of
class <TT>X</TT> following the function's <I>declarator-id</I>
[<I>footnote:</I>
That is, an unqualified name that occurs, for instance, in a type or default
argument expression in the <I>parameter-declaration-clause</I>, in the
function body, or in an expression of a <I>mem-initializer</I> in a constructor
definition.
<I>end footnote</I>] shall be ...</BLOCKQUOTE>
<BR>
<BR>
<HR>
<A NAME="33"></A>
<H4>33.
  
Argument dependent lookup and overloaded functions
</H4>
<B>Section: </B>3.4.2&nbsp;



 <A HREF="basic.html#basic.lookup.argdep">basic.lookup.argdep</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Jason Merrill
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>15 Jul 1998<BR>





<P>If an argument used for lookup is the address of a group of overloaded
functions, are there any associated namespaces or classes? What if it's
the address of a function template?</P>

<P>My inclination is to say no to both.</P>

<P>
<U>From Mike Miller:</U>
</P>

<P>We discussed this on the reflector a few weeks ago. I'll leave the template
case for the Core III experts, but I'd find it surprising if the overload
case weren't handled as the obvious generalization of the single-function
case. For a single function, the associated namespaces are those of the
types used in the parameters and return type; I would expect that using
an overloaded function name would simply be the union of the namespaces
from the members of the overload set. That would be the simplest and most
intuitive, IMHO &mdash; is there an argument for doing it differently?</P>

<P>
<B>Proposed Resolution (04/99):</B>
In 3.4.2&nbsp;



 <A HREF="basic.html#basic.lookup.argdep">basic.lookup.argdep</A>
 paragraph 2,
add following the last bullet in the list of associated classes and namespaces
for various argument types (not a bullet itself because overload sets and
templates do not have a type):</P>
<BLOCKQUOTE>In addition, if the argument is the name or address of a set
of overloaded functions and/or function templates, its associated classes
and namespaces are the union of those associated with each of the members
of the set: the namespace in which the function or function template is
defined and the classes and namespaces associated with its (non-dependent)
parameter types and return type.</BLOCKQUOTE>
<BR>
<BR>
<HR>
<A NAME="90"></A>
<H4>90.
  
Should the enclosing class be an "associated class" too?
</H4>
<B>Section: </B>3.4.2&nbsp;



 <A HREF="basic.html#basic.lookup.argdep">basic.lookup.argdep</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>John Spicer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>2 Feb 1999<BR>





<P>Section
3.4.2&nbsp;



 <A HREF="basic.html#basic.lookup.argdep">basic.lookup.argdep</A>

 includes the following:</P>
<UL>
<LI>
If T is a class type, its associated classes are the class itself and its
direct and indirect base classes. Its associated namespaces are the namespaces
in which its associated classes are defined.</LI>

<LI>
If T is a union or enumeration type, its associated namespace is the namespace
in which it is defined. If it is a class member, its associated class is
the member's class; else it has no associated class.</LI>
</UL>
Note that for a union, the enclosing class is an "associated class", but
for a class type the enclosing class is not an "associated class". This
results in some surprising behavior, as shown in the example below.
<PRE>
    struct A {
        union U {};
        friend void f(U);
    };
            
    struct B {
        struct S {};
        friend void f(S);
    };
             
    int main() { 
        A::U    u; 
        f(u);        // okay: A is an associated class
        B::S    s;
        f(s);        // error: no matching f(), B is not an associated class
    }

</PRE>
Certainly the enclosing class should also be an associated class for nested
class types, shouldn't it?

<P>
<B>Proposed Resolution (10/99):</B>
Change the two referenced bullets to read:</P>
<UL>
<LI>If <TT>T</TT> is a class type (including unions),
its associated classes are:
the class itself; the
class of which it is a member, if any; and its direct and indirect base
classes. Its associated namespaces are the namespaces in which its
associated classes are defined.</LI>

<LI>If <TT>T</TT> is an enumeration type,
its associated namespace is the namespace in
which it is defined. If it is class member, its associated class is the
member's class; else it has no associated class.</LI>
</UL>
(This proposal also addresses
<A HREF="
     cwg_closed.html#91">Core issue 91</A>.)
<BR>
<BR>
<HR>
<A NAME="164"></A>
<H4>164.
  
Overlap between Koenig and normal lookup
</H4>
<B>Section: </B>3.4.2&nbsp;



 <A HREF="basic.html#basic.lookup.argdep">basic.lookup.argdep</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Derek Inglis
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>3 Sep 1999<BR>



<P>The description of Koenig lookup in
3.4.2&nbsp;



 <A HREF="basic.html#basic.lookup.argdep">basic.lookup.argdep</A>
 paragraph 1 says,</P>

<BLOCKQUOTE>
...other namespaces not considered during the usual unqualified lookup
(3.4.1&nbsp;



 <A HREF="basic.html#basic.lookup.unqual">basic.lookup.unqual</A>
) may be
searched.
</BLOCKQUOTE>

Does this mean that Koenig lookup does <I>not</I> search namespaces
that were already searched during the usual unqualified lookup?  The
answer is academic except for the two-stage lookup during template
instantiation.  If a given namespace is searched in the context of the
template definition, are declarations in that namespace in the
instantiation context ignored during the Koenig lookup?  For instance,

<PRE>
    void f(int);

    template &lt;class T&gt; void g(T t) {
        f(t);
    }

    enum E { e };

    void f(E);

    void h() {
        g(e);
    }
</PRE>

In this example, the call <TT>f(t)</TT> in the template function will
resolve to <TT>f(E)</TT> if Koenig lookup reexamines already-searched
namespaces and to <TT>f(int)</TT> if not.

<P>
<B>Proposed Resolution (10/00):</B>
</P>

<P>Immediately preceding the example
at the end of
3.4.2&nbsp;



 <A HREF="basic.html#basic.lookup.argdep">basic.lookup.argdep</A>
 paragraph 2, add
the following:</P>

<BLOCKQUOTE>
[<I>Note:</I> the namespaces and classes associated with the argument
types can include namespaces and classes already considered by the
ordinary unqualified lookup.]
</BLOCKQUOTE>
<BR>
<BR>
<HR>
<A NAME="85"></A>
<H4>85.
  
Redeclaration of member class
</H4>
<B>Section: </B>3.4.4&nbsp;



 <A HREF="basic.html#basic.lookup.elab">basic.lookup.elab</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Adamczyk
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>25 Jan 1999<BR>



<P>In
3.4.4&nbsp;



 <A HREF="basic.html#basic.lookup.elab">basic.lookup.elab</A>

 paragraph 3, there is the example</P>
<PRE>
    struct Base {
        // ...
        struct Data { /* ... */ };  // <I>Defines nested </I>Data
        struct Data;                // <I>OK: Redeclares nested </I>Data
    };
</PRE>

The final redeclaration is invalid according to
9.2&nbsp;



 <A HREF="class.html#class.mem">class.mem</A> paragraph 1 last sentence.

<P>
<B>Proposed resolution (10/00):</B> Remove the line</P>

<PRE>
        struct Data;                // <I>OK: Redeclares nested </I>Data
</PRE>

<P>See also
<A HREF="
     cwg_active.html#36">Core issue 36</A>
 and
<A HREF="
     cwg_defects.html#56">Core issue 56</A>.</P>
<BR>
<BR>
<HR>
<A NAME="89"></A>
<H4>89.
  
Object lifetime does not account for reference rebinding
</H4>
<B>Section: </B>3.8&nbsp;



 <A HREF="basic.html#basic.life">basic.life</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>AFNOR
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>27 Oct 1998<BR>



<BR>From J16/98-0026 = WG21 N1169, "Proposed Defect Reports on ISO/IEC
14882, Programming Languages - C++":
<BLOCKQUOTE>
A reference is rebindable. This is surprising and unnatural. This can
also cause subtle optimizer bugs.

<P>Example:</P>
<PRE>
    struct T {
        int&amp; ri;
        T (int&amp; r) : ri (r) { }
    };
    
    void bar (T*);
    
    void foo () {
        int i;
        T x (i);
        x.ri = 3;   // the optimizer understands that this is really i = 3
        bar (&amp;x);
        x.ri = 4;   // optimizer assumes that this writes to i, but this is incorrect
    }
    
    int gi;
    
    void bar (T* p) {
        p-&gt;~T ();
        new (p) T (gi);
    }
</PRE>
If we replace <TT>T&amp;</TT> with <TT>T* const</TT> in the example then
undefined behavior result and the optimizer is correct.

<P>Proposal: make <TT>T&amp;</TT> equivalent to <TT>T* const</TT> by extending
the scope of
3.8&nbsp;



 <A HREF="basic.html#basic.life">basic.life</A>
 paragraph
9 to references.</P>
</BLOCKQUOTE>
<P>(See also J16/99-0005 = WG21 N1182, "Proposed Resolutions for Core
Language Issues 6, 14, 20, 40, and 89")</P>

<P>In addition, Lisa Lippincott pointed out the following example:</P>

<PRE>
    void f( const bool * );
    void g();

    int main() {
       const bool *b = new const bool( false );
       f(b);
       if (*b)
          g();
    }

    void f( const bool *b ) {
       new ( const_cast&lt;bool *&gt;(b) ) const bool( true );
    }
</PRE>

<P>The proposed wording in the paper would still permit this usage and
thus prevent an optimizer from eliminating the call to <TT>g()</TT>.</P>

<P>
<B>Proposed Resolution (10/00):</B>
</P>

<P>Add a new bullet to the list of restrictions in
3.8&nbsp;



 <A HREF="basic.html#basic.life">basic.life</A>
paragraph 7, following the second bullet ("the new object is of the same
type..."):</P>
<UL>
<LI>
the type of the original object is not const-qualified, and,
if a class type, does not contain any non-static
data member whose type is const-qualified or a reference type, and</LI>
</UL>
<BR>
<BR>
<HR>
<A NAME="93"></A>
<H4>93.
  
Missing word in 3.8 <U>basic.life</U> paragraph 2
</H4>
<B>Section: </B>3.8&nbsp;



 <A HREF="basic.html#basic.life">basic.life</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>6 Feb 1999<BR>





<P>The text of
3.8&nbsp;



 <A HREF="basic.html#basic.life">basic.life</A>

 paragraph
2 currently reads,</P>
<UL>[<I>Note:</I> the lifetime of an array object or of an object of
type (3.9&nbsp;



 <A HREF="basic.html#basic.types">basic.types</A>


) starts...]</UL>
<P>The phrase "an object of type" is obviously incorrect. I believe it should
read "an object of POD type." Does anyone disagree?</P>

<P>
<B>Proposed Resolution (10/99):</B>
As suggested.</P>
<BR>
<BR>
<HR>
<A NAME="43"></A>
<H4>43.
  
Copying base classes (PODs) using memcpy
</H4>
<B>Section: </B>3.9&nbsp;



 <A HREF="basic.html#basic.types">basic.types</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Nathan Myers
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>15 Sep 1998<BR>





<P>Can you use memcpy on non-member POD subobjects of non-POD objects?</P>

<P>In 3.9&nbsp;



 <A HREF="basic.html#basic.types">basic.types</A>
 paragraphs 2 and 3 we have:</P>
<BLOCKQUOTE>For any complete POD object type <TT>T</TT>, whether or not the object
holds a valid value of type <TT>T</TT>, the underlying bytes
(1.7&nbsp;



 <A HREF="intro.html#intro.memory">intro.memory</A>
) making
up the object can be copied into an array of <TT>char</TT>
or <TT>unsigned char</TT>*. If the content of
the array of <TT>char</TT> or <TT>unsigned char</TT> is copied back into the object, the
object shall subsequently hold its original value. <I>[Example elided]</I>
<BLOCKQUOTE>*[<I>Footnote:</I> By using, for example, the library functions
(17.4.1.2&nbsp;



 <A HREF="lib-intro.html#lib.headers">lib.headers</A>
)
<TT>memcpy</TT> or <TT>memmove</TT>. <I>end footnote</I>]</BLOCKQUOTE>
For any POD type <TT>T</TT>, if two pointers to <TT>T</TT> point
to distinct <TT>T</TT> objects <TT>obj1</TT>
and <TT>obj2</TT>, if the value of <TT>obj1</TT> is copied into
<TT>obj2</TT>, using the <TT>memcpy</TT> library
function, <TT>obj2</TT> shall subsequently hold the same value as
<TT>obj1</TT>.</BLOCKQUOTE>
Paragraph 3 doesn't repeat the restriction of paragraph 2. Should it be
assumed? Otherwise only complete POD types are copyable to an array of
<TT>char</TT> and back, but scribbling over subobjects is OK.
(Or perhaps a "distinct <TT>T</TT> object" is a complete object...)

<P>
<B>Proposed Resolution (04/99):</B>
Change the text in 3.9&nbsp;



 <A HREF="basic.html#basic.types">basic.types</A>

paragraph 2 from:</P>
<BLOCKQUOTE>For any complete POD object type <TT>T</TT>, ...</BLOCKQUOTE>
to:
<BLOCKQUOTE>For any object (other than a base class subobject) of POD type
<TT>T</TT>, ...</BLOCKQUOTE>
Change the text in 3.9&nbsp;



 <A HREF="basic.html#basic.types">basic.types</A>
 paragraph 3 from:
<BLOCKQUOTE>For any POD type <TT>T</TT>, if two pointers to <TT>T</TT>
point to distinct <TT>T</TT> objects <TT>obj1</TT> and <TT>obj2</TT>,</BLOCKQUOTE>
to:
<BLOCKQUOTE>For any POD type <TT>T</TT>, if two pointers to <TT>T</TT>
point to distinct <TT>T</TT> objects <TT>obj1</TT> and <TT>obj2</TT>,
where neither <TT>obj1</TT> nor <TT>obj2</TT> is a base class subobject,
...</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="149"></A>
<H4>149.
  
Accessibility and ambiguity
</H4>
<B>Section: </B>4.10&nbsp;



 <A HREF="conv.html#conv.ptr">conv.ptr</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Nathan Sidwell
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>31 Jul 1999<BR>



<P>The Standard uses confusing terminology when referring to
accessibility in connection with ambiguity.  For instance:</P>

<P>4.10&nbsp;



 <A HREF="conv.html#conv.ptr">conv.ptr</A>
 paragraph 3:</P>

<BLOCKQUOTE>
If <TT>B</TT> is an inaccessible or ambiguous base ...
</BLOCKQUOTE>

5.2.7&nbsp;



 <A HREF="expr.html#expr.dynamic.cast">expr.dynamic.cast</A>
 paragraph 8:

<BLOCKQUOTE>
... has an unambiguous public base ...
</BLOCKQUOTE>

10.3&nbsp;



 <A HREF="derived.html#class.virtual">class.virtual</A>
 paragraph 5:

<BLOCKQUOTE>
... is an unambiguous direct or indirect base ... and
is accessible ...
</BLOCKQUOTE>

15.3&nbsp;



 <A HREF="except.html#except.handle">except.handle</A>
 paragraph 3:

<BLOCKQUOTE>
not involving conversions to pointers to private or
protected or ambiguous classes
</BLOCKQUOTE>

<P>The phrase "unambiguous public base" is unfortunate as it
could mean either "an
unambiguous base not considering accessibility, which is public"
or "an
unambiguous base considering only the publicly accessible bases."
I believe the
former interpretation correct, as accessibility is applied after visibility
(11&nbsp;



 <A HREF="access.html#class.access">class.access</A>
 paragraph 4)
and ambiguity is described in terms of visibility
(10.2&nbsp;



 <A HREF="derived.html#class.member.lookup">class.member.lookup</A>
 paragraph 2).</P>

<P>Suggested Resolution:
Use the phrases "public and unambiguous,"
"accessible and unambiguous,"
"non-public or ambiguous," or "inaccessible or ambiguous" as appropriate.</P>

<P>
<B>Proposed resolution (10/00):</B>
<UL>
<LI>
5.2.7&nbsp;



 <A HREF="expr.html#expr.dynamic.cast">expr.dynamic.cast</A>
 paragraph 8,
bullet 2: change "unambiguous public base class" to "unambiguous
and public base class"</LI>
<LI>
10.3&nbsp;



 <A HREF="derived.html#class.virtual">class.virtual</A>
 paragraph 5: change
"the class in the return type... is an unambiguous direct or
indirect base class... and is accessible in <TT>D</TT>" to "the
class in the return type... is an unambiguous and accessible direct
or indirect base class..."</LI>
</UL>
</P>
<BR>
<BR>
<HR>
<A NAME="123"></A>
<H4>123.
  
Bad cross-reference
</H4>
<B>Section: </B>5.1&nbsp;



 <A HREF="expr.html#expr.prim">expr.prim</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>3 June 1999<BR>





The cross-reference is incorrect in the first
sentence after the grammar in
5.1&nbsp;



 <A HREF="expr.html#expr.prim">expr.prim</A>
 paragraph 7:

<BLOCKQUOTE>
A <I>nested-name-specifier</I> that names a class, optionally
followed by the keyword <TT>template</TT>
(14.8.1&nbsp;



 <A HREF="template.html#temp.arg.explicit">temp.arg.explicit</A>
), ...
</BLOCKQUOTE>

The use of the <TT>template</TT> keyword in this context is discussed
in 14.2&nbsp;



 <A HREF="template.html#temp.names">temp.names</A>
, not
14.8.1&nbsp;



 <A HREF="template.html#temp.arg.explicit">temp.arg.explicit</A>
.  

<BR>
<BR>
<HR>
<A NAME="147"></A>
<H4>147.
  
Naming the constructor
</H4>
<B>Section: </B>5.1&nbsp;



 <A HREF="expr.html#expr.prim">expr.prim</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>John Spicer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>21 Feb 1999<BR>



<P>From paper J16/99-0010 = WG21 N1187.</P>

<P>5.1&nbsp;



 <A HREF="expr.html#expr.prim">expr.prim</A>
 paragraph 7 says that
<I>class-name::class-name</I> names the constructor when both
<I>class-name</I> refer to the same class.  (Note the different
perspective, at least, in
12.1&nbsp;



 <A HREF="special.html#class.ctor">class.ctor</A>
 paragraph 1, in which
constructors have no names and are recognized by syntactic context
rather than by name.)</P>

<P>This formulation does not address the case of classes in which a
function template is declared as a constructor, for example:</P>

<PRE>
    template &lt;class T&gt; struct A {
        template &lt;class T2&gt; A(T2);
    };
    template&lt;&gt; template&lt;&gt; A&lt;int&gt;::A&lt;int&gt;(int);
</PRE>

<P>Here there is an ambiguity as to whether the second template argument
list is for the injected class name or for the constructor.</P>

<P>Suggested resolution: restate the rule as a component of name
lookup.  Specifically, if when doing a qualified lookup in a given
class you look up a name that is the same as the name of the class,
the entity found is the constructor and not the injected class name.
In all other cases, the name found is the injected class name.  For
example:</P>

<PRE>
    class B { };
    class A: public B {
        A::B ab;       // B is the inherited injected B
        A::A aa;       // Error: A::A is the constructor
    };
</PRE>

<P>Without this rule some very nasty backtracking is needed.  For
example, if the injected class name could be qualified by its own
class name, the following code would be well-formed:</P>

<PRE>
    template &lt;class T&gt; struct A {
        template &lt;class T2&gt; A(T2);
        static A x;
    };
    template&lt;&gt; A&lt;int&gt;::A&lt;int&gt;(A&lt;int&gt;::x);
</PRE>

<P>Here the declarator for the definition of the static data member
has redundant parentheses, and it's only after seeing the declarator
that the parser can know that the second <TT>A&lt;int&gt;</TT> is the
injected class name rather than the constructor.</P>

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>In
9&nbsp;



 <A HREF="class.html#class">class</A>
 paragraph 2, change</P>

<BLOCKQUOTE>
The <I>class-name</I> is also inserted into the scope of the class
itself.  For purposes of access checking the inserted class name...
</BLOCKQUOTE>

<P>to</P>

<BLOCKQUOTE>
The <I>class-name</I> is also inserted into the scope of the class
itself; this is known as the <I>injected-class-name</I>.  For purposes
of access checking, the injected-class-name...
</BLOCKQUOTE>

<P>Also, in 3.4.3.1&nbsp;



 <A HREF="basic.html#class.qual">class.qual</A>, add the following
before paragraph 2:</P>

<BLOCKQUOTE>
If the <I>nested-name-specifier</I> nominates a class <TT>C</TT>, and the
name specified after the <I>nested-name-specifier</I>, when looked up in
<TT>C</TT>, is the injected-class-name of <TT>C</TT> (clause
9&nbsp;



 <A HREF="class.html#class">class</A>), the name is instead considered
to name the constructor of class <TT>C</TT>.  Such a constructor name
shall only be used in the <I>declarator-id</I> of a constructor
definition that appears outside of the class definition.
[<I>Example:</I>

<PRE>
    struct A { A(); };
    struct B: public A { B(); };

    A::A() { }
    B::B() { }

    B::A ba;    // object of type A
    A::A a;     // error, A::A is not a type name
</PRE>

&mdash;<I>end example</I>]
</BLOCKQUOTE>

<P>Also, change 3.4&nbsp;



 <A HREF="basic.html#basic.lookup">basic.lookup</A> paragraph 3 from</P>

<BLOCKQUOTE>

Because the name of a class is inserted in its class scope (clause
9&nbsp;



 <A HREF="class.html#class">class</A>), the name of a class is also considered a
member of that class for the purposes of name hiding and lookup.

</BLOCKQUOTE>

<P>to</P>

<BLOCKQUOTE>

The injected-class-name of a class (clause 9&nbsp;



 <A HREF="class.html#class">class</A>) is
also considered to be a member of that class for the purposes of name
hiding and lookup.

</BLOCKQUOTE>

<P>(See also <A HREF="
     cwg_defects.html#194">issue 194</A>.)</P>
<BR>
<BR>
<HR>
<A NAME="52"></A>
<H4>52.
  
Non-static members, member selection and access checking
</H4>
<B>Section: </B>5.2.5&nbsp;



 <A HREF="expr.html#expr.ref">expr.ref</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Adamczyk
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>13 Oct 1998<BR>



<P>5.2.5&nbsp;



 <A HREF="expr.html#expr.ref">expr.ref</A>
 paragraph 4 should make
it clear that when a nonstatic member is referenced in a member
selection operation, the type of the left operand is implicitly cast
to the naming class of the member. This allows for the detection of
access and ambiguity errors on that implicit cast.</P>

<P>
<B>Proposed Resolution (10/00):</B>
</P>

<OL>

<LI>
<P>In 11.2&nbsp;



 <A HREF="access.html#class.access.base">class.access.base</A> paragraph 4, remove the following
from the second note:</P>

<BLOCKQUOTE>

If the member <TT>m</TT> is accessible when named in the naming
class according to the rules below, the access to <TT>m</TT> is
nonetheless ill-formed if the type of <TT>p</TT> cannot be
implicitly converted to type <TT>T</TT> (for example, if <TT>T</TT> is an
inaccessible base class of <TT>p</TT>'s class).

</BLOCKQUOTE>
</LI>

<LI>
<P>Add the following as a new paragraph 5 of
11.2&nbsp;



 <A HREF="access.html#class.access.base">class.access.base</A>:</P>

<BLOCKQUOTE>

If a class member access operator, including an
implicit "<TT>this-&gt;</TT>," is used to access a nonstatic
data member or nonstatic member function, the
reference is ill-formed if the left operand
(considered as a pointer in the "." operator case)
cannot be implicitly converted to a pointer to the
naming class of the right operand.  [<I>Note:</I> this
requirement is in addition to the requirement that the
member be accessible as named.]

</BLOCKQUOTE>
</LI>

<LI>
<P>In 11.2&nbsp;



 <A HREF="access.html#class.access.base">class.access.base</A> paragraph 4, fix a typographical
error by adding the missing right parenthesis following the text</P>

<BLOCKQUOTE>

(including cases where an implicit "<TT>this-&gt;</TT>" is added

</BLOCKQUOTE>
</LI>

<LI>
<P>Add following the first sentence of
5.2.2&nbsp;



 <A HREF="expr.html#expr.call">expr.call</A> paragraph 4:</P>

<BLOCKQUOTE>

If the function is a nonstatic member function, the
"<TT>this</TT>" parameter of the function (9.3.2&nbsp;



 <A HREF="class.html#class.this">class.this</A>) shall
be initialized with a pointer to the object of the
call, converted as if by an explicit type conversion
(5.4&nbsp;



 <A HREF="expr.html#expr.cast">expr.cast</A>).  [<I>Note:</I> there is no access checking on
this conversion; the access checking is done as part of
the (possibly implicit) class member access operator.
See 11.2&nbsp;



 <A HREF="access.html#class.access.base">class.access.base</A>.]

</BLOCKQUOTE>
</LI>

</OL>
<BR>
<BR>
<HR>
<A NAME="53"></A>
<H4>53.
  
Lvalue-to-rvalue conversion before certain static_casts
</H4>
<B>Section: </B>5.2.9&nbsp;



 <A HREF="expr.html#expr.static.cast">expr.static.cast</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Adamczyk
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>13 Oct 1998<BR>



<P>Section 5.2.9&nbsp;



 <A HREF="expr.html#expr.static.cast">expr.static.cast</A>
 paragraph 6
should make it clear that when any of the
"inverse of any standard conversion sequence" static_casts are done, the
operand undergoes the lvalue-to-rvalue conversions first.</P>

<P>
<B>Proposed Resolution (10/00):</B>
</P>

<P>In 5.2.9&nbsp;



 <A HREF="expr.html#expr.static.cast">expr.static.cast</A> paragraph 6, change</P>

<BLOCKQUOTE>

can be performed explicitly using <TT>static_cast</TT> subject to the
restriction that the explicit conversion does not cast away constness
(5.2.11&nbsp;



 <A HREF="expr.html#expr.const.cast">expr.const.cast</A>), ...

</BLOCKQUOTE>

<P>to</P>

<BLOCKQUOTE>

can be performed explicitly using <TT>static_cast</TT>.  <B>The
lvalue-to-rvalue (4.1&nbsp;



 <A HREF="conv.html#conv.lval">conv.lval</A>), array-to-pointer
(4.2&nbsp;



 <A HREF="conv.html#conv.array">conv.array</A>), and function-to-pointer (4.3&nbsp;



 <A HREF="conv.html#conv.func">conv.func</A>) conversions are applied to the operand.  Such a
<TT>static_cast</TT> is</B> subject to the restriction that it does
not cast away constness (5.2.11&nbsp;



 <A HREF="expr.html#expr.const.cast">expr.const.cast</A>), ...

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="128"></A>
<H4>128.
  
Casting between enum types
</H4>
<B>Section: </B>5.2.9&nbsp;



 <A HREF="expr.html#expr.static.cast">expr.static.cast</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Clark Nelson
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>10 June 1999<BR>





<P>According to 7.2&nbsp;



 <A HREF="dcl.html#dcl.enum">dcl.enum</A>
 paragraph 9,
it is permitted to convert from one enumeration type to another.
However, neither 5.2.9&nbsp;



 <A HREF="expr.html#expr.static.cast">expr.static.cast</A>

nor 5.4&nbsp;



 <A HREF="expr.html#expr.cast">expr.cast</A>
 allows this
conversion.</P>

<P>
<B>Proposed resolution (10/00):</B> Change the first two sentences of
5.2.9&nbsp;



 <A HREF="expr.html#expr.static.cast">expr.static.cast</A>
 paragraph 7 to read</P>

<BLOCKQUOTE>
A value of integral <B>or enumeration</B> type can be explicitly
converted to an enumeration type.  The value is unchanged if the
<B>original</B> value is within the range of the enumeration values
(7.2&nbsp;



 <A HREF="dcl.html#dcl.enum">dcl.enum</A>
).
</BLOCKQUOTE>
<BR>
<BR>
<HR>
<A NAME="137"></A>
<H4>137.
  
<TT>static_cast</TT> of <I>cv</I> <TT>void*</TT>
</H4>
<B>Section: </B>5.2.9&nbsp;



 <A HREF="expr.html#expr.static.cast">expr.static.cast</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>13 July 1999<BR>





<P>According to 5.2.9&nbsp;



 <A HREF="expr.html#expr.static.cast">expr.static.cast</A>

paragraph 10,</P>

<BLOCKQUOTE>
An rvalue of type "pointer to <I>cv</I> <TT>void</TT>" can be explicitly
converted to a pointer to object type.
</BLOCKQUOTE>

No requirements are stated regarding the cv-qualification of the
pointer to object type.  Contrast this with the formula used in
paragraphs 5, 8, and 9, where the treatment of cv-qualification
is explicit, requiring that the target type be at least as
cv-qualified as the source.

There is an apparently general requirement on all forms of
<TT>static_cast</TT> in
5.2.9&nbsp;



 <A HREF="expr.html#expr.static.cast">expr.static.cast</A>
 paragraph 1 that it
"shall not cast away constness."
Assuming that this restriction applies to paragraph 10, since there is
no explicit exception to the general rule, that still leaves
open the question of whether one can "cast away volatility"
in a conversion from <TT>volatile void*</TT> to a pointer to object
type.

Should 5.2.9&nbsp;



 <A HREF="expr.html#expr.static.cast">expr.static.cast</A>
 paragraph 10
be rewritten to handle cv-qualification in
the same way as paragraphs 5, 8, and 9?

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>Change the first sentence of
5.2.9&nbsp;



 <A HREF="expr.html#expr.static.cast">expr.static.cast</A>
 paragraph 10 to</P>
<BLOCKQUOTE>
An rvalue of type "pointer to <I>cv1</I> <TT>void</TT>" can be
converted to an rvalue of type "pointer to <I>cv2</I> <TT>T</TT>", where
<TT>T</TT> is an object type and <I>cv2</I> is the same cv-qualification
as, or greater cv-qualification than, <I>cv1</I>.
</BLOCKQUOTE>
<BR>
<BR>
<HR>
<A NAME="74"></A>
<H4>74.
  
Enumeration value in direct-new-declarator
</H4>
<B>Section: </B>5.3.4&nbsp;



 <A HREF="expr.html#expr.new">expr.new</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Jason Merrill
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>16 Nov 1998<BR>





<P>5.3.4&nbsp;



 <A HREF="expr.html#expr.new">expr.new</A>

paragraph 6 says:</P>
<BLOCKQUOTE>The expression in a <I>direct-new-declarator</I> shall have integral
type (3.9.1&nbsp;



 <A HREF="basic.html#basic.fundamental">basic.fundamental</A>
) with a non-negative
value.</BLOCKQUOTE>
I assume the intent was to also allow enumeral types, as we do in
5.2.1&nbsp;



 <A HREF="expr.html#expr.sub">expr.sub</A>

?

<P>
<B>Proposed Resolution (10/99):</B>
Replace "integral type" by "integral or enumeration type" in
5.3.4&nbsp;



 <A HREF="expr.html#expr.new">expr.new</A>
 paragraph 6.</P>
<BR>
<BR>
<HR>
<A NAME="127"></A>
<H4>127.
  
Ambiguity in description of matching deallocation function
</H4>
<B>Section: </B>5.3.4&nbsp;



 <A HREF="expr.html#expr.new">expr.new</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Alexander Schiemann
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>8 June 1999<BR>



<P>If a placement allocation function has default arguments for all its
parameters except the first, it can be called using non-placement
syntax.  In such a case, it is not clear whether
the deallocation function to be called if the constructor terminates
by throwing an expression is determined on the basis of
the syntax of the <I>new-expression</I> (i.e., a non-placement
deallocation function)
or the declaration of the selected (placement) allocation function.
5.3.4&nbsp;



 <A HREF="expr.html#expr.new">expr.new</A>
 paragraph 19 indicates
that the deallocation function must match the declaration of the
allocation function.
However, 15.2&nbsp;



 <A HREF="except.html#except.ctor">except.ctor</A>
 says that the
distinction is based on whether the <I>new-expression</I> contains
a <I>new-placement</I> or not.</P>

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>In 15.2&nbsp;



 <A HREF="except.html#except.ctor">except.ctor</A> paragraph 2, replace</P>

<BLOCKQUOTE>

If the object or array was allocated in a <I>new-expression</I> and
the <I>new-expression</I> does not contain a <I>new-placement</I>, the
deallocation function (3.7.3.2&nbsp;



 <A HREF="basic.html#basic.stc.dynamic.deallocation">basic.stc.dynamic.deallocation</A>, 12.5&nbsp;



 <A HREF="special.html#class.free">class.free</A>) is called to free the storage occupied by the object;
the deallocation function is chosen as specified in 5.3.4&nbsp;



 <A HREF="expr.html#expr.new">expr.new</A>. If the object or array was allocated in a
<I>new-expression</I> and the <I>new-expression</I> contains a
<I>new-placement</I>, the storage occupied by the object is
deallocated only if an appropriate placement operator delete is found,
as specified in 5.3.4&nbsp;



 <A HREF="expr.html#expr.new">expr.new</A>.

</BLOCKQUOTE>

<P>with</P>

<BLOCKQUOTE>

If the object or array was allocated in a <I>new-expression</I>, the
matching deallocation function (3.7.3.2&nbsp;



 <A HREF="basic.html#basic.stc.dynamic.deallocation">basic.stc.dynamic.deallocation</A>,
5.3.4&nbsp;



 <A HREF="expr.html#expr.new">expr.new</A>, 12.5&nbsp;



 <A HREF="special.html#class.free">class.free</A>), if any, is
called to free the storage occupied by the object.

</BLOCKQUOTE>

<P>See also <A HREF="
     cwg_defects.html#429">issue 429</A>.</P>

<BR>
<BR>
<HR>
<A NAME="179"></A>
<H4>179.
  
Function pointers and subtraction
</H4>
<B>Section: </B>5.7&nbsp;



 <A HREF="expr.html#expr.add">expr.add</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>Nov 1999<BR>



<P>5.7&nbsp;



 <A HREF="expr.html#expr.add">expr.add</A>
 paragraph 8 explicitly
allows subtraction of two pointers to functions:</P>

<BLOCKQUOTE>
If two pointers point to the same object <B>or function</B>... and the
two pointers are subtracted...
</BLOCKQUOTE>

However, 5.7&nbsp;



 <A HREF="expr.html#expr.add">expr.add</A>
 paragraph 2
requires that two pointers that are subtracted be pointers to an
<B>object</B> type; function pointers are not allowed.

<P>Being able to subtract two pointers to functions doesn't seem
terribly useful, especially considering that subtracting two pointers
to different functions appears to produce undefined behavior rather
than simply a non-zero result, according to paragraph 6:</P>

<BLOCKQUOTE>
Unless both pointers point to elements of the same array object, or
one past the last element of the array object, the behavior is
undefined.
</BLOCKQUOTE>

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>Remove the words <B>or function</B>
from paragraph 8.</P>
<BR>
<BR>
<HR>
<A NAME="73"></A>
<H4>73.
  
Pointer equality
</H4>
<B>Section: </B>5.10&nbsp;



 <A HREF="expr.html#expr.eq">expr.eq</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Nathan Myers
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>13 Nov 1998<BR>





<P>
<U>Nathan Myers</U>: In
5.10&nbsp;



 <A HREF="expr.html#expr.eq">expr.eq</A>
, we have:</P>
<BLOCKQUOTE>Pointers to objects or functions of the same type (after pointer
conversions) can be compared for equality. Two pointers of the same type
compare equal if and only if they are both null, both point to the same
object or function, or both point one past the end of the same array.</BLOCKQUOTE>
What does this say, when we have
<PRE>
    int i[1];
    int j[1];
</PRE>
about the expression <TT>(i+1 == j)</TT> ? It seems to require padding
between <TT>i[0]</TT> and <TT>j[0]</TT> so that the comparison will come
out false.
<BR>
<BR>I think this may be a defect, in that the quoted paragraph extends
operator=='s domain too far beyond operator&lt;'s. It should permit
(but not require) an off-the-end pointer to compare equal to another
object, but not to any element of the same array.

<P>
<U>Mike Miller</U>: I think this is reading more into the statement
in
5.10&nbsp;



 <A HREF="expr.html#expr.eq">expr.eq</A>

 paragraph 1 than is actually
there. What does it mean for a pointer to "point to" an object?
I can't find anything that definitively says that <TT>i+1</TT> cannot "point
to" <TT>j[0]</TT> (although it's obviously not required to do so).
If <TT>i+1</TT> is allowed to "point to" <TT>j[0]</TT>, then <TT>i+1==j</TT>
is allowed to be true, and there's no defect. There are places where
aliasing is forbidden, but the N+1th element of an array doesn't appear
to be one of them.</P>

<P>To put it another way, "points to" is undefined in the Standard. The
only definition I can think of that encompasses the possible ways in which
a pointer can get its value (e.g., the implementation-defined conversion
of an arbitrary integer value to a pointer) is that it means "having the
same value representation as would be produced by applying the (builtin)
&amp; operator to an lvalue expression designating that object".
In other words, if the bits are right, it doesn't matter how you produced
the value, as long as you didn't perform any operations that have undefined
results. The expression <TT>i+1</TT> is not undefined, so if the
bits of <TT>i+1</TT> are the same as those of <TT>&amp;j[0]</TT>, then
<TT>i+1</TT> "points to" <TT>j[0]</TT> and <TT>i+i==j</TT> is allowed to
be true.</P>

<P>
<U>Tom MacDonald</U>: C9X contains the following words for the "=="
operator:</P>
<BLOCKQUOTE>Two pointers compare equal if both are null pointers, both
are pointers to the same object (including a pointer to an object and a
subobject at its beginning) or function, both are pointers to one
past the last element of the same array object, or one is a pointer to
one past the end of one array object and the other is a pointer to the
start of a different array object that happens to immediately follow the
first array object in the address space.</BLOCKQUOTE>
<U>Matt Austern</U>: I don't think there's anything wrong with saying that
the result of
<PRE>
    int x[1];
    int y[1]; 
    std::cout &lt;&lt; (y == x + 1) &lt;&lt; std::endl;
</PRE>
is implementation defined, or even that it's undefined.

<P>
<U>Mike Miller</U>: A similar question could be raised about different
objects that (sequentially) share the same storage. Consider the following:</P>
<PRE>
    struct B {
        virtual void f();
    };
    struct D1: B { };
    struct D2: B { };
    void g() {
        B* bp1 = new D1;
        B* bp2 = new (bp1) D2;
        bp1 == bp2; // ???
    }
</PRE>
Section
3.8&nbsp;



 <A HREF="basic.html#basic.life">basic.life</A>

 paragraph 5 does
not list this kind of comparison among the pointer operations that cause
undefined behavior, so presumably the comparison is allowed. However,
5.10&nbsp;



 <A HREF="expr.html#expr.eq">expr.eq</A>

paragraph 1 describes pointer comparison in terms of "[pointing] to the
same object," which <TT>bp1</TT> and <TT>bp2</TT> clearly do not do. How
should we describe the result of this comparison?

<P>
<U>Jason Merrill</U>:
When you consider comparing pointers to void, this seems to suggest that no
two objects can have the same address, depending on your interpretation of
"point to the same object."  This would cripple the empty base
optimization.</P>

<P>3.9.2&nbsp;



 <A HREF="basic.html#basic.compound">basic.compound</A>
 refers to 'pointers
to void or objects or functions'.  In that case,
5.10&nbsp;



 <A HREF="expr.html#expr.eq">expr.eq</A>
 does
not allow you to compare them; it only allows comparing pointers to
objects and functions.</P>

<P>
<B>Proposed Resolution (10/00):</B>
</P>

<UL>

<LI>

In 3.9.2&nbsp;



 <A HREF="basic.html#basic.compound">basic.compound</A> paragraph 3, add the following
wording immediately preceding, "The value representation of pointer
types is implementation-defined":

<BLOCKQUOTE>

A valid value of an object pointer type represents either the address
of a byte in memory (1.7&nbsp;



 <A HREF="intro.html#intro.memory">intro.memory</A>) or a null pointer
(4.10&nbsp;



 <A HREF="conv.html#conv.ptr">conv.ptr</A>).  If an object of type <TT>T</TT> is
located at an address <TT>A</TT>, a pointer of type <I>cv</I>
<TT>T*</TT> whose value is the address <TT>A</TT> is said to <I>point
to</I> that object, regardless of how the value was obtained.
[<I>Note:</I> for instance, the address one past the end of an array
(5.7&nbsp;



 <A HREF="expr.html#expr.add">expr.add</A>) would be considered to point to an
unrelated object of the array's element type that might be located at
that address.]

</BLOCKQUOTE>

</LI>
<LI>

In 5.10&nbsp;



 <A HREF="expr.html#expr.eq">expr.eq</A> paragraph 1, change the sentence
beginning, "Two pointers of the same type..." to read:

<BLOCKQUOTE>

Two pointers of the same type compare equal if and only if they are
both null, both point to the same function, or both represent the same
address (3.9.2&nbsp;



 <A HREF="basic.html#basic.compound">basic.compound</A>).

</BLOCKQUOTE>

</LI>
</UL>

<P>(See also paper J16/00-0011 = WG21 N1234.)</P>
<BR>
<BR>
<HR>
<A NAME="188"></A>
<H4>188.
  
Comma operator and rvalue conversion
</H4>
<B>Section: </B>5.18&nbsp;



 <A HREF="expr.html#expr.comma">expr.comma</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>20 Dec 1999<BR>





<P>Given</P>
 
<PRE>
    char arr[100];
    sizeof(0,arr);
</PRE>
 
<P>What does the <TT>sizeof</TT> expression return?  According to
5.18&nbsp;



 <A HREF="expr.html#expr.comma">expr.comma</A>
 paragraph 1,
the comma operator yields
an lvalue if the second argument is an lvalue.  Since
4.2&nbsp;



 <A HREF="conv.html#conv.array">conv.array</A>
 paragraph 1 says that the
array-to-pointer conversion yields an rvalue, it seems that
<TT>sizeof</TT> should see an array type and give the answer <TT>100</TT>.
If so, the value of the <TT>sizeof</TT> expression would be
different from that of the corresponding expression in C, but there
is nothing in Annex
C&nbsp;



 <A HREF="diff.html#diff">diff</A>
to indicate that an incompatible change was intended.</P>

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>Add the following as paragraph 3 of C.1.3&nbsp;



 <A HREF="diff.html#diff.expr">diff.expr</A>:</P>

<BLOCKQUOTE>

<P>
<B>5.16, 5.17, 5.18</B>
</P>

<P>
<B>Change:</B> The result of a conditional expression, an
assignment expression, or a comma expression may be an lvalue.<BR>
<B>Rationale:</B> C++ is an object-oriented language, placing
relatively more emphasis on lvalues. For example, functions may return
lvalues.<BR>
<B>Effect on original feature:</B> Change to semantics of well-defined
feature.  Some C expressions that implicitly rely on lvalue-to-rvalue
conversions will yield different results.  For example,

<PRE>
    char arr[100];
    sizeof(0, arr)
</PRE>

yields <TT>100</TT> in C++ and <TT>sizeof(char*)</TT> in C.<BR>
<B>Difficulty of converting:</B> Programs must add explicit casts to
the appropriate rvalue.<BR>
<B>How widely used:</B> Rare.
</P>

</BLOCKQUOTE>
<BR>
<BR>
<HR>
<A NAME="94"></A>
<H4>94.
  
Inconsistencies in the descriptions of constant expressions
</H4>
<B>Section: </B>5.19&nbsp;



 <A HREF="expr.html#expr.const">expr.const</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>8 Feb 1999<BR>





<OL>
<LI>
According to
9.4.2&nbsp;



 <A HREF="class.html#class.static.data">class.static.data</A>
 paragraph 4, a static const integral or const enumeration data member initialized
with an integral constant expression "can appear in integral constant expressions
<B>within its scope</B>" [emphasis mine]. This means that the following
is not permitted:

<PRE>
    struct S {
        static const int c = 5;
    };
    int a[S::c];    // error: S::c not in scope
</PRE>
Is this restriction intentional? If so, what was the rationale for the
restriction?

<P>
<U>Bjarne Stroustrup</U>: I think that once you have said <TT>S::</TT>,
<TT>c</TT> is in scope so that</P>
<PRE>
    int a[S::c];
</PRE>
is ok.
    
<P>
<U>Mike Miller</U>: I'd like to think that's what it meant, but I
don't believe that's what it said. According to
3.3&nbsp;



 <A HREF="basic.html#basic.scope">basic.scope</A>
 paragraph 1, the scope of
a name is the region "in which that name may be used as an unqualified
name." You can, indeed, use a qualified name to refer to a name that
is not in scope, but that only goes to reinforce my point that
"<TT>S::c</TT>" is not in scope at the point where the expression
containing it is used. I think the phrase "within its scope" is at
best misleading and should be removed. (Unless there's a reason I'm
missing for restricting the use of static member constants to their
scope.)</P>
</LI>
<LI>
According to 5.19&nbsp;



 <A HREF="expr.html#expr.const">expr.const</A>
 paragraph
1, integral constant expressions can "involve...const variables or static
data members of integral or enumeration types initialized with constant
expressions." However, in 5.19&nbsp;



 <A HREF="expr.html#expr.const">expr.const</A>
paragraph 3, arithmetic constant expressions cannot include them. This
seems a rather gratuitous distinction and one likely to bite programmers
trained always to use const variables instead of preprocessor definitions.
Again, is there a rationale for the difference?

<P>As far as I can tell from 5.19&nbsp;



 <A HREF="expr.html#expr.const">expr.const</A>
paragraph 2, "arithmetic constant expressions" (as distinct from "integral
constant expressions") are used only in static initializers to distinguish
between static and dynamic initialization. They include floating point
types and exclude non-type template parameters, as well as the const variables
and static data members.</P>
<LI>
<P>There is a minor error in 5.19&nbsp;



 <A HREF="expr.html#expr.const">expr.const</A>
paragraph 2. The first sentence says, "Other expressions are considered
constant expressions only for the purpose of non-local static object initialization."
However, 6.7&nbsp;



 <A HREF="stmt.html#stmt.dcl">stmt.dcl</A>
 paragraph 4 appears
to rely on the same definition dealing with the initialization of local
static objects. I think that the words "non-local" should be dropped and
a cross reference to 6.7&nbsp;



 <A HREF="stmt.html#stmt.dcl">stmt.dcl</A>
added.</P>
</LI>
<LI>
5.19&nbsp;



 <A HREF="expr.html#expr.const">expr.const</A>
paragraph 4 says, "An expression
that designates the address of a member or base class of a non-POD class
object (clause 9) is not an address constant expression (12.7&nbsp;



 <A HREF="special.html#class.cdtor">class.cdtor</A>
)."
    
<P>I'm guessing that should be "non-static member," like the similar
prohibition in 12.7&nbsp;



 <A HREF="special.html#class.cdtor">class.cdtor</A>
 regarding
out-of-lifetime access to members of non-POD class objects.</P>
</LI>
</LI>
</OL>

<P>
<B>Proposed resolutions (10/00):</B>
</P>

<OL>
<LI>
<P>Remove the phrase "within its scope" in
9.4.2&nbsp;



 <A HREF="class.html#class.static.data">class.static.data</A>
 paragraph 4.</P>
</LI>
<LI>

Replace 5.19&nbsp;



 <A HREF="expr.html#expr.const">expr.const</A> paragraph 3 with the following:

<BLOCKQUOTE>

An <I>arithmetic constant expression</I> shall satisfy the
requirements for an integral constant expression, except that

<UL>
<LI>floating literals need not be cast to integral or enumeration
type, and</LI>
<LI>conversions to floating point types are permitted.</LI>
</UL>

</BLOCKQUOTE>
</LI>
<LI>
<P>This is not a defect; no change is required.  The suggested
wording would be more accurate, but since the effect on local
initialization is unobservable the current wording is adequate.</P>
</LI>

<LI>
<P>Change the referenced sentence in 5.19&nbsp;



 <A HREF="expr.html#expr.const">expr.const</A>
paragraph 4 to "An expression that designates the address of a
subobject of a non-POD class object is not an address constant
expression."</P>
</LI>
</OL>
<BR>
<BR>
<HR>
<A NAME="227"></A>
<H4>227.
  
How many scopes in an <TT>if</TT> statement?
</H4>
<B>Section: </B>6.4&nbsp;



 <A HREF="stmt.html#stmt.select">stmt.select</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Marc Paterno
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>21 Apr 2000<BR>


<P>The wording of 6.4&nbsp;



 <A HREF="stmt.html#stmt.select">stmt.select</A> paragraph 1 is
misleading.  Instead of</P>

<BLOCKQUOTE>

The substatement in a <I>selection-statement</I> (both substatements,
in the <TT>else</TT> form of the <TT>if</TT> statement) implicitly
defines a local scope (3.3&nbsp;



 <A HREF="basic.html#basic.scope">basic.scope</A>).

</BLOCKQUOTE>

<P>it should say</P>

<BLOCKQUOTE>

... <B>each substatement</B>, in the <TT>else</TT> form...

</BLOCKQUOTE>

<P>As is, one is left with the impression that both "then" and "else"
clauses together form a single scope.</P>

<P>
<B>Proposed resolution (10/00):</B> As suggested.</P>

<BR>
<BR>
<HR>
<A NAME="69"></A>
<H4>69.
  
Storage class specifiers on template declarations
</H4>
<B>Section: </B>7.1.1&nbsp;



 <A HREF="dcl.html#dcl.stc">dcl.stc</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Ball
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>17 Oct 1998<BR>



<P>
<U>Mike Ball:</U> I cannot find anything in the standard that tells me the meaning of
a <I>storage-class-specifier</I> on a function template declaration. In
particular, there is no indication what effect, if any, it has on the storage
class of the instantiations.</P>

<P>There is an explicit prohibition of <I>storage-class-specifier</I>s
on explicit specializations.</P>

<P>For example, if we have</P>
<PRE>
    template&lt;class T&gt; static int foo(T) { return sizeof(T); }
</PRE>
does this generate static functions for all instantiations? By
7.1.1&nbsp;



 <A HREF="dcl.html#dcl.stc">dcl.stc</A>

the storage class applies to the name declared in the declarator, which
is the template <TT>foo</TT>, not an instantiation of <TT>foo</TT>, which
is named with a <I>template-id</I>. There is a statement in clause
14 that template names have linkage, which supports the contention that
"<TT>static</TT>" applies to the template, not to instantiations.

<P>So what does the specifier mean? Lacking a direct statement in
the standard, I see the following posibilities, in my preference order.</P>
<OL>
<LI>
<I>storage-class-specifier</I>s have no meaning on template declarations,
their use being subsumed by "<TT>export</TT>" (for the template name) and
the unnamed namespace (for instantiations)</LI>

<LI>
<I>storage-class-specifier</I>s have no effect on the template name, but
do affect the linkage of the instantiations, though this now applies linkage
to <I>template-id</I>s, which I can find no support for. I suspect
this is what was intended, though I don't remember</LI>
</OL>
Of course, if anybody can find some concrete statement, that would settle
it.

<P>
<U>From John Spicer</U>
</P>

<P>The standard does say that a namespace scope template has external linkage
unless it is a function template declared "static". It doesn't explicitly
say that the linkage of the template is also the linkage of the instantiations,
but I believe that is the intent. For example, a storage class is
prohibited on an explicit specialization to ensure that a specialization
cannot be given a different storage class than the template on which it
is based.</P>
<BLOCKQUOTE>
<U>Mike</U>: This makes sense, but I couldn't find much support
in the document. Sounds like yet another interpretation to add to
the list.

<P>
<U>John</U>: Agreed.</P>
</BLOCKQUOTE>
The standard does not talk about the linkage of instantiations, because
only "names" are considered to have linkage, and instances are not really
names. So, from an implementation point of view, instances have linkage,
but from a language point of view, only the template from which the instances
are generated has linkage.
<BLOCKQUOTE>
<U>Mike</U>: Which is why I think it would be cleaner to eliminate
storage class specifiers entirely and rely on the unnamed namespace.
There is a statement that specializations go into the namespace of the
template. No big deal, it's not something it says, so we live with
what's there.

<P>
<U>John</U>: That would mean prohibiting static function templates.
I doubt those are common, but I don't really see much motivation for getting
rid of them at this point.</P>
</BLOCKQUOTE>
"export" is an additional attribute that is separate from linkage, but
that can only be applied to templates with external linkage.
<BLOCKQUOTE>
<U>Mike</U>: I can't find that restriction in the standard,
though there is one that templates in an unnamed namespace can't be exported.
I'm pretty sure that we intended it, though.

<P>
<U>John</U>: I can't find it either. The "inline" case seems to
be addressed, but not static. Surely this is an error as, by definition,
a static template can't be used from elsewhere.</P>
</BLOCKQUOTE>

<P>
<B>Proposed resolution (10/00):</B>
</P>
Change the text in 14&nbsp;



 <A HREF="template.html#temp">temp</A> paragraph 4 from:
<BLOCKQUOTE>
A template name may have linkage (3.5&nbsp;



 <A HREF="basic.html#basic.link">basic.link</A>).
</BLOCKQUOTE>
to:
<BLOCKQUOTE>
A template name has linkage (3.5&nbsp;



 <A HREF="basic.html#basic.link">basic.link</A>).
A non-member function template
can have internal linkage; any other template name shall have external
linkage. Entities generated from a template with internal linkage are distinct
from all entities generated in other translation units.
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="56"></A>
<H4>56.
  
Redeclaring typedefs within classes
</H4>
<B>Section: </B>7.1.3&nbsp;



 <A HREF="dcl.html#dcl.typedef">dcl.typedef</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Adamczyk
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>13 Oct 1998<BR>



<P>Can a typedef redeclaration be done within a class?</P>
<PRE>
    class X { 
        typedef int I; 
        typedef int I; 
    };
</PRE>
See also
9.2&nbsp;



 <A HREF="class.html#class.mem">class.mem</A>
,
<A HREF="
     cwg_active.html#36">Core issue 36</A>,
and
<A HREF="
     cwg_defects.html#85">Core issue 85</A>.

<P>
<B>Proposed Resolution (10/99):</B>
Change 7.1.3&nbsp;



 <A HREF="dcl.html#dcl.typedef">dcl.typedef</A>
 paragraph 2
from "In a given scope" to "In a given non-class scope."</P>
<BR>
<BR>
<HR>
<A NAME="76"></A>
<H4>76.
  
Are const volatile variables considered "constant expressions"?
</H4>
<B>Section: </B>7.1.5.1&nbsp;



 <A HREF="dcl.html#dcl.type.cv">dcl.type.cv</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Judy Ward
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>15 Dec 1998<BR>



<P>The following code does not compile with the EDG compiler:</P>
<PRE>
    volatile const int a = 5;
    int b[a];
</PRE>
The standard,
7.1.5.1&nbsp;



 <A HREF="dcl.html#dcl.type.cv">dcl.type.cv</A>
, says:
<BLOCKQUOTE>A variable of const-qualified integral or enumeration type
initialized by an integral constant expression can be used in integral
constant expressions.</BLOCKQUOTE>
This doesn't say it can't be const volatile-qualified, although I think
that was what was intended.

<P>
<B>Proposed Resolution (10/99):</B>
Change the referenced text in paragraph 2 of
7.1.5.1&nbsp;



 <A HREF="dcl.html#dcl.type.cv">dcl.type.cv</A>
 to read:</P>

<UL>A variable of <B>non-volatile</B> const-qualified ...</UL>
<BR>
<BR>
<HR>
<A NAME="68"></A>
<H4>68.
  
Grammar does not allow "friend class A&lt;int&gt;;"
</H4>
<B>Section: </B>7.1.5.3&nbsp;



 <A HREF="dcl.html#dcl.type.elab">dcl.type.elab</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Ball
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>17 Oct 1998<BR>



<P>I can't find the answer to the following in the standard. Does
anybody have a reference?</P>

<P>The syntax for elaborated type specifier is
<UL>
<I>elaborated-type-specifier</I>:
<UL>
<I>class-key</I> <TT>::</TT><SUB>opt</SUB> <I>nested-name-specifier<SUB>opt</SUB>
identifier</I>
<BR>
<TT>enum</TT> <TT>::</TT><I><SUB>opt</SUB> nested-name-specifier<SUB>opt</SUB>
identifier</I>
<BR>
<TT>typename</TT> <TT>::</TT><SUB>opt</SUB>&nbsp;
<I>nested-name-specifier</I> <I>identifier</I>
<BR>
<TT>typename</TT> <TT>::</TT><SUB>opt</SUB>&nbsp;
<I>nested-name-specifier</I> <TT>template</TT><SUB>opt</SUB>&nbsp;<I>template-id</I>
</UL>
<BR>
If an <I>elaborated-type-specifier</I> is the sole constituent of a declaration,
the declaration is ill-formed unless it is an explicit specialization
(14.7.3&nbsp;



 <A HREF="template.html#temp.expl.spec">temp.expl.spec</A>
),
an explicit instantiation
(14.7.2&nbsp;



 <A HREF="template.html#temp.explicit">temp.explicit</A>
) or it has one of the following
forms:
<BR>
<BR>
<UL>
<I>class-key</I> <I>identifier</I> <TT>;</TT>
<BR>
<TT>friend</TT> <I>class-key</I> <I>identifier</I> <TT>;</TT>
<BR>
<TT>friend</TT> <I>class-key</I> <TT>::</TT> <I>identifier</I> <TT>;</TT>
<BR>
<TT>friend</TT> <I>class-key</I> <I>nested-name-specifier</I>&nbsp;<I>identifier</I>&nbsp;<TT>;</TT>
</UL>
</UL>
Which does not allow the production</P>
<PRE>
    class foo&lt;int&gt; // foo is a template
</PRE>
On the other hand, a friend declaration seems to require this production,
<BLOCKQUOTE>An <I>elaborated-type-specifier</I> shall be used in a
friend declaration for a class.*

<P>[<I>Footnote:</I> The <I>class-key</I> of the
<I>elaborated-type-specifier</I> is required.
&mdash;<I>end footnote</I>]</P>
</BLOCKQUOTE>
And in 14.5.3&nbsp;



 <A HREF="template.html#temp.friend">temp.friend</A>
 we find the example
<BLOCKQUOTE>
[<I>Example:</I>
<PRE>
    template&lt;class T&gt; class task;
    template&lt;class T&gt; task&lt;T&gt;* preempt(task&lt;T&gt;*);

    template&lt;class T&gt; class task {
        // ...
        friend void next_time();
        friend void process(task&lt;T&gt;*);
        friend task&lt;T&gt;* preempt&lt;T&gt;(task&lt;T&gt;*);
        template&lt;class C&gt; friend int func(C);

        friend class task&lt;int&gt;;
        template&lt;class P&gt; friend class frd;
        // ...
    };
</PRE>
</BLOCKQUOTE>
Is there some special dispensation somewhere to allow the syntax in this
context?  Is there something I've missed about <I>elaborated-type-specifier</I>?
Is it just another bug in the standard?

<P>An additional problem was reported via <TT>comp.std.c++</TT>: the
grammar does not allow the following example:</P>

<PRE>
    namespace A{
      class B{};
    };

    namespace B{
      class A{};
      class C{
	friend class ::A::B;
      };
    };
</PRE>

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>Change the grammar in 7.1.5.3&nbsp;



 <A HREF="dcl.html#dcl.type.elab">dcl.type.elab</A> to read<BR>
<UL>
<I>elaborated-type-specifier:</I>
<UL>
<I>class-key</I> <TT>::<SUB>opt</SUB></TT>
<I>nested-name-specifier<SUB>opt</SUB> identifier</I>
</UL>
<UL>
<I>class-key</I> <TT>::<SUB>opt</SUB></TT>
<I>nested-name-specifier<SUB>opt</SUB></I>
<TT>template<SUB>opt</SUB></TT> <I>template-id</I>
</UL>
<UL>
<TT>enum ::<SUB>opt</SUB></TT>
<I>nested-name-specifier<SUB>opt</SUB> identifier</I>
</UL>
<UL>
<TT>typename ::<SUB>opt</SUB></TT> <I>nested-name-specifier
identifier</I>
</UL>
<UL>
<TT>typename ::<SUB>opt</SUB></TT> <I>nested-name-specifier</I>
<TT>template<SUB>opt</SUB></TT> <I>template-id</I>
</UL>
</UL>

and change the forms allowed in paragraph 1 to
<UL>
<I>class-key identifier</I> <TT>;</TT>
<BR>
<TT>friend</TT> <I>class-key</I> <TT>::<SUB>opt</SUB></TT> <I>identifier</I>
<TT>;</TT>
<BR>
<TT>friend</TT> <I>class-key</I> <TT>::<SUB>opt</SUB></TT> <I>template-id</I>
<TT>;</TT>
<BR>
<TT>friend</TT> <I>class-key</I> <TT>::<SUB>opt</SUB></TT>
<I>nested-name-specifier identifier</I> <TT>;</TT>
<BR>
<TT>friend</TT> <I>class-key</I> <TT>::<SUB>opt</SUB></TT>
<I>nested-name-specifier</I> <TT>template<SUB>opt</SUB></TT>
<I>template-id</I> <TT>;</TT>
</UL>
</P>
<BR>
<BR>
<HR>
<A NAME="171"></A>
<H4>171.
  
Global namespace scope
</H4>
<B>Section: </B>7.3&nbsp;



 <A HREF="dcl.html#basic.namespace">basic.namespace</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Greg Lutz
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>19 Sep 1999<BR>



<P>7.3&nbsp;



 <A HREF="dcl.html#basic.namespace">basic.namespace</A>
 paragraph 2 says:</P>

<BLOCKQUOTE>
A name declared outside all named namespaces, blocks
(6.3&nbsp;



 <A HREF="stmt.html#stmt.block">stmt.block</A>
) and
classes (clause 9&nbsp;



 <A HREF="class.html#class">class</A>
) has
global namespace scope
(3.3.5&nbsp;



 <A HREF="basic.html#basic.scope.namespace">basic.scope.namespace</A>
).
</BLOCKQUOTE>

But 3.3.5&nbsp;



 <A HREF="basic.html#basic.scope.namespace">basic.scope.namespace</A>

paragraph 3 says:

<BLOCKQUOTE>
A name declared outside all named or unnamed namespaces
(7.3&nbsp;



 <A HREF="dcl.html#basic.namespace">basic.namespace</A>
),
blocks (6.3&nbsp;



 <A HREF="stmt.html#stmt.block">stmt.block</A>
),
function declarations
(8.3.5&nbsp;



 <A HREF="decl.html#dcl.fct">dcl.fct</A>
),
function definitions
(8.4&nbsp;



 <A HREF="decl.html#dcl.fct.def">dcl.fct.def</A>
) and classes
(clause 9&nbsp;



 <A HREF="class.html#class">class</A>
) has global
namespace scope (also called global scope).
</BLOCKQUOTE>

7.3&nbsp;



 <A HREF="dcl.html#basic.namespace">basic.namespace</A>

should evidently be changed to match the wording in
3.3.5&nbsp;



 <A HREF="basic.html#basic.scope.namespace">basic.scope.namespace</A>

&mdash; the unnamed namespace is <I>not</I> global scope.

<P>
<B>Proposed resolution (10/00):</B> </P>

<OL>

<LI>
<P>Replace the first sentence of 3.3.5&nbsp;



 <A HREF="basic.html#basic.scope.namespace">basic.scope.namespace</A>
paragraph 3 with</P>

<BLOCKQUOTE>

The outermost declarative region of a translation unit is also a
namespace, called the <I>global namespace</I>.  A name declared in the
global namespace has <I>global namespace scope</I> (also called
<I>global scope</I>).

</BLOCKQUOTE>
</LI>

<LI>
<P>In the last sentence of the same paragraph, change "Names
declared in the global namespace scope" to "Names with global
namespace scope."</P>
</LI>

<LI>
<P>Replace 7.3&nbsp;



 <A HREF="dcl.html#basic.namespace">basic.namespace</A> paragraph 2 with

<BLOCKQUOTE>

The outermost declarative region of a translation unit is a namespace;
see 3.3.5&nbsp;



 <A HREF="basic.html#basic.scope.namespace">basic.scope.namespace</A>.

</BLOCKQUOTE>
</P>
</LI>

</OL>

<BR>
<BR>
<HR>
<A NAME="166"></A>
<H4>166.
  
Friend declarations of <I>template-id</I>s
</H4>
<B>Section: </B>7.3.1.2&nbsp;



 <A HREF="dcl.html#namespace.memdef">namespace.memdef</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>John Spicer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>8 Sep 1999<BR>





<P>
<U>John Spicer</U>:
I believe the standard is not clear with respect to this example:</P>

<PRE>
    namespace N {
      template &lt;class T&gt; void f(T);
      namespace M {
        struct A {
          friend void f&lt;int&gt;(int);  // okay - refers to N::f
        };
      }
    }
</PRE>

At issue is whether the friend declaration refers to <TT>N::f</TT>, or
whether it is invalid.

<P>A note in
3.3.1&nbsp;



 <A HREF="basic.html#basic.scope.pdecl">basic.scope.pdecl</A>
 paragraph 6 says</P>

<BLOCKQUOTE>
friend declarations refer to functions or classes
that are members of the nearest enclosing namespace ...
</BLOCKQUOTE>

I believe it
is intended to mean <I>unqualified</I> friend declarations.  Certainly
<TT>friend void A::B()</TT> need not refer
to a member of the nearest enclosing
namespace.  Only when the declarator is unqualified (i.e., it is a declaration
and not a reference) does this rule need to apply.  The presence of an
explicit template argument list requires
that a previous declaration be visible and renders this a reference and not
a declaration that is subject to this rule.

<P>
<U>Mike Miller</U>:
7.3.1.2&nbsp;



 <A HREF="dcl.html#namespace.memdef">namespace.memdef</A>
 paragraph 3 says,</P>

<BLOCKQUOTE>
When looking for a prior declaration of a
class or a function declared as a friend, scopes outside the
innermost enclosing namespace scope are not considered.
</BLOCKQUOTE>

On the other hand, the friend declaration would be a syntax
error if <TT>f</TT> weren't declared as a template name; it would
seem very strange not to find the declaration that made the
friend declaration syntactically correct.

However, it also seems strange to treat this case differently
from ordinary functions and from templates:

<PRE>
    namespace N {
      template &lt;class T&gt; void f(T);
      void g();
      namespace M {
        struct A {
          friend void f&lt;int&gt;(int);               // N::f
          template &lt;class T&gt; friend void f(T);   // M::f
          friend void g();                       // M::g
        };
      }
    }
</PRE>

<P>
<U>John Spicer</U>:
This section refers to "looking for a prior declaration".  This
gets back to an earlier discussion we've had about the difference between
matching two declarations of the same name and doing name lookup.  I would
maintain that in <TT>f&lt;int&gt;</TT>
the <TT>f</TT> is looked up using a normal lookup.  In
practice, this is really how it has to be done because the declaration
could actually be <TT>f&lt;int&gt;::x</TT>.</P>

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>In
7.3.1.2&nbsp;



 <A HREF="dcl.html#namespace.memdef">namespace.memdef</A>
 paragraph 3, change</P>

<BLOCKQUOTE>
When looking for a prior declaration of a class or a function declared
as a friend, scopes outside the innermost enclosing namespace scope are
not considered.
</BLOCKQUOTE>

to

<BLOCKQUOTE>
When looking for a prior declaration of a class or a function declared
as a friend, and when the name of the friend class or function is
neither a qualified name nor a <I>template-id</I>, scopes outside the
innermost enclosing namespace scope are not considered.
</BLOCKQUOTE>

Also, change the example in that paragraph as follows:

<PRE>
    void h(int);
    template &lt;class T&gt; void f2(T);
    namespace A {
        class X {
            friend void f(X);       // A::f(X) is a friend
            friend void f2&lt;&gt;(int);  // ::f2&lt;&gt;(int) is a friend
    ...
</PRE>

<P>(See also issues
<A HREF="
     cwg_closed.html#95">95</A>,
<A HREF="
     cwg_defects.html#136">136</A>,
<A HREF="
     cwg_active.html#138">138</A>,
<A HREF="
     cwg_defects.html#139">139</A>,
<A HREF="
     cwg_defects.html#143">143</A>, and
<A HREF="
     cwg_closed.html#165">165</A>.)</P>
<BR>
<BR>
<HR>
<A NAME="101"></A>
<H4>101.
  
Redeclaration of extern "C" names via using-declarations
</H4>
<B>Section: </B>7.3.3&nbsp;



 <A HREF="dcl.html#namespace.udecl">namespace.udecl</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>10 Mar 1999<BR>





<P>Consider the following:</P>
<PRE>
    extern "C" void f();
    namespace N {
        extern "C" void f();
    }
    using N::f;
</PRE>
According to
7.3.3&nbsp;



 <A HREF="dcl.html#namespace.udecl">namespace.udecl</A>

paragraph 11, the <I>using-declaration</I> is an error:
<BLOCKQUOTE>
If a function declaration in namespace scope or block
scope has the same name and the same parameter types
as a function introduced by a <I>using-declaration</I>, the
program is ill-formed.
</BLOCKQUOTE>
Based on the context (7.3.3&nbsp;



 <A HREF="dcl.html#namespace.udecl">namespace.udecl</A>

paragraph 10 simply reiterates the requirements
of
3.3&nbsp;



 <A HREF="basic.html#basic.scope">basic.scope</A>
), one might wonder if
the failure to exempt <TT>extern&nbsp;"C"</TT>
functions was intentional or an oversight.  After all, there is
only one function <TT>f()</TT> involved, because it's <TT>extern&nbsp;"C"</TT>, so
ambiguity is not a reason to prohibit the <I>using-declaration</I>.
<P>
This also breaks the relatively strong parallel between <TT>extern&nbsp;"C"</TT>
functions and typedefs established in our discussion of
<A HREF="
     cwg_closed.html#14">Core issue 14</A>
in Santa Cruz.  There the question was for <I>using-directives</I>:</P>
<PRE>
    typedef unsigned int size_t;
    extern "C" int f();
    namespace N {
        typedef unsigned int size_t;
        extern "C" int f();
    }
    using namespace N;
    int i = f();        // ambiguous "f"?
    size_t x;           // ambiguous "size_t"?
</PRE>
We decided for both that there was no ambiguity because each
pair of declarations declares the same entity.  (According to
3&nbsp;



 <A HREF="basic.html#basic">basic</A>

paragraph 3, a typedef name is not an entity, but a type is; thus the
declarations of <TT>size_t</TT> declare the same entity "<TT>unsigned int</TT>".)
<P>
In the context of <I>using-declaration</I>s, there is no explicit
extension of the restrictions in 3.3&nbsp;



 <A HREF="basic.html#basic.scope">basic.scope</A>

paragraph 4 except as noted above for function declarations; thus the parallel
scenario for a typedef is not ill-formed:</P>
<PRE>
    typedef unsigned int size_t;
    namespace N {
        typedef unsigned int size_t;
    };
    using N::size_t;        // okay, both declarations
                            // refer to the same entity
</PRE>
I think the first sentence of
7.3.3&nbsp;



 <A HREF="dcl.html#namespace.udecl">namespace.udecl</A>

paragraph 11 ought to be rewritten as:
<BLOCKQUOTE>
If a function declaration in namespace scope or block
scope has the same name and the same parameter types
as a function introduced by a <I>using-declaration</I>,
<B>and the declarations do not declare the same function</B>, the
program is ill-formed.
</BLOCKQUOTE>

<P>
<B>Proposed Resolution (10/99):</B>
As suggested.</P>
<BR>
<BR>
<HR>
<A NAME="103"></A>
<H4>103.
  
Is it <I>extended-namespace-definition</I> or <I>extension-namespace-definition</I> ?
</H4>
<B>Section: </B>7.3.4&nbsp;



 <A HREF="dcl.html#namespace.udir">namespace.udir</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Herb Sutter
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>20 Mar 1999<BR>





<P>
Section 7.3.4&nbsp;



 <A HREF="dcl.html#namespace.udir">namespace.udir</A>

paragraph 3 uses the term <I>extended-namespace-definition</I> three times:</P>
<BLOCKQUOTE>
If a namespace is extended by an <I>extended-namespace-definition</I> after a
<I>using-directive</I> for that namespace is given, the additional members of
the extended namespace and the members of namespaces nominated by
<I>using-directive</I>s in the <I>extended-namespace-definition</I> can be used
after the <I>extended-namespace-definition</I>.
</BLOCKQUOTE>
I think the intent is clear, but unfortunately I cannot find any other
mention (or definition) of this term.
<P>
<U>Mike Miller</U>: True enough; in
Section 7.3.1&nbsp;



 <A HREF="dcl.html#namespace.def">namespace.def</A>

[the grammar] it's called an <I>extension-namespace-definition</I>.</P>

<P>
<B>Proposed Resolution (10/99):</B>
Systematically replace "extended-namespace-definition" by "extension-namespace-definition".</P>
<BR>
<BR>
<HR>
<A NAME="40"></A>
<H4>40.
  
Syntax of <I>declarator-id</I>
</H4>
<B>Section: </B>8.3&nbsp;



 <A HREF="decl.html#dcl.meaning">dcl.meaning</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>01 Sep 1998<BR>



<P>(From J16/99-0005 = WG21 N1182, "Proposed Resolutions for Core
Language Issues 6, 14, 20, 40, and 89")</P>

<P>There are two sub-issues. The first concerns the statement in
8.3&nbsp;



 <A HREF="decl.html#dcl.meaning">dcl.meaning</A>


paragraph 1,</P>
<BLOCKQUOTE>The <I>id-expression</I> of a <I>declarator-id</I> shall be
a simple identifier except for the declaration of some special functions
(12.3&nbsp;



 <A HREF="special.html#class.conv">class.conv</A>
,
12.4&nbsp;



 <A HREF="special.html#class.dtor">class.dtor</A>
,
13.5&nbsp;



 <A HREF="over.html#over.oper">over.oper</A>
) and for the declaration
of template specializations or partial specializations
(14.7&nbsp;



 <A HREF="template.html#temp.spec">temp.spec</A>
).</BLOCKQUOTE>
The second sub-issue is regarding another statement in the same paragraph:
<BLOCKQUOTE>A <I>declarator-id</I> shall not be qualified except for the
definition of a member function (9.3&nbsp;



 <A HREF="class.html#class.mfct">class.mfct</A>
)
or static data member (9.4&nbsp;



 <A HREF="class.html#class.static">class.static</A>
)
or nested class (9.7&nbsp;



 <A HREF="class.html#class.nest">class.nest</A>
) outside
of its class, the definition or explicit instantiation of a function, variable
or class member of a namespace outside of its namespace, or...</BLOCKQUOTE>
<U>Analysis</U>

<P>The problem in the first sub-issue is that the wrong syntactic non-terminal
is mentioned. The relevant portions of the grammar are:</P>
<UL>
<I>declarator-id </I>:
<UL>
<I>id-expression</I>
<BR>
<TT>::</TT><SUB>opt</SUB>&nbsp; <I>nested-name-specifier</I><SUB>opt</SUB>
<I>type-name</I>
</UL>
<I>id-expression </I>:
<UL>
<I>unqualified-id</I>
<BR>
<I>qualified-id</I>
</UL>
<I>unqualified-id </I>:
<UL>
<I>identifier</I>
<BR>
<I>operator-function-id</I>
<BR>
<I>conversion-function-id</I>
<BR>~ <I>class-name</I>
<BR>
<I>template-id</I>
</UL>
</UL>
The exceptions in the citation from
8.3&nbsp;



 <A HREF="decl.html#dcl.meaning">dcl.meaning</A>


paragraph 1 are all the non-identifier cases of <I>unqualified-id</I>:
12.3&nbsp;



 <A HREF="special.html#class.conv">class.conv</A>


is for <I>conversion-function-id</I>s,
12.4&nbsp;



 <A HREF="special.html#class.dtor">class.dtor</A>


is for destructors,
13.5&nbsp;



 <A HREF="over.html#over.oper">over.oper</A>

 is
for overloaded operators, and
14.7&nbsp;



 <A HREF="template.html#temp.spec">temp.spec</A>


is for <I>template-id</I>s. If taken literally, this sentence would exclude
all <I>qualified-id</I>s, which it obviously is not intended to do. Instead,
the apparent intent is something along the lines of
<BLOCKQUOTE>If an <I>unqualified-id</I> is used as the <I>id-expression</I>
of a <I>declarator-id</I>, it shall be a simple identifier except...</BLOCKQUOTE>
However, it does not appear that this restriction has any meaning; all
of the possible cases of <I>unqualified-id</I>s are represented in the
list of exceptions! Rather than recasting the sentence into a correct but
useless form, it would be better to remove it altogether.

<P>The second sub-issue deals with the conditions under which a <I>qualified-id</I>
can be used in a declarator, including "the definition of a...nested class"
and "the definition or explicit instantiation of a...class member of a
namespace." However, the name in a class definition is not part of a declarator;
these constructs do not belong in a list of declarator contexts.</P>

<P>
<B>Proposed Resolution for sub-issue 1 (04/99):</B>
</P>
<P>The suggested resolution for the first sub-issue overlooked the
fact that the existing wording has the additional effect of prohibiting
the use of the non-identifier syntax for declaring other than the
listed entities.  Thus the proposed wording
for the first sub-issue is:</P>
<P>Change 8.3&nbsp;



 <A HREF="decl.html#dcl.meaning">dcl.meaning</A>
 paragraph 1 from:</P>
<BLOCKQUOTE>The <I>id-expression</I> of a <I>declarator-id</I> shall be a simple <I>identifier</I> except...</BLOCKQUOTE>
to:
<BLOCKQUOTE>An <I>unqualified-id</I> occurring in a <I>declarator-id</I> shall be a simple <I>identifier</I> except...</BLOCKQUOTE>

<P>
<B>Proposed Resolution for sub-issue 2 (10/99):</B>
</P>

<P>Change 8.3&nbsp;



 <A HREF="decl.html#dcl.meaning">dcl.meaning</A>
 paragraph 1 from:</P>
<BLOCKQUOTE>A <I>declarator-id</I> shall not be qualified except for the
definition of a member function (9.3&nbsp;



 <A HREF="class.html#class.mfct">class.mfct</A>
)
or static data member (9.4&nbsp;



 <A HREF="class.html#class.static">class.static</A>
)
or nested class (9.7&nbsp;



 <A HREF="class.html#class.nest">class.nest</A>
) outside
of its class, the definition or explicit instantiation of a function, variable
or class member of a namespace outside of its namespace, or...</BLOCKQUOTE>

to

<BLOCKQUOTE>A <I>declarator-id</I> shall not be qualified except for the
definition of a member function (9.3&nbsp;



 <A HREF="class.html#class.mfct">class.mfct</A>
)
or static data member (9.4&nbsp;



 <A HREF="class.html#class.static">class.static</A>
)
outside
of its class, the definition or explicit instantiation of a function or
variable member of a namespace outside of its namespace, or...</BLOCKQUOTE>
<BR>
<BR>
<HR>
<A NAME="159"></A>
<H4>159.
  
Namespace qualification in declarators
</H4>
<B>Section: </B>8.3&nbsp;



 <A HREF="decl.html#dcl.meaning">dcl.meaning</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>John Spicer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>23 Aug 1999<BR>



<P>8.3&nbsp;



 <A HREF="decl.html#dcl.meaning">dcl.meaning</A>
 paragraph 1 says:</P>

<BLOCKQUOTE>
In the qualified <I>declarator-id</I> for a class or namespace member
definition that appears outside of the member's class or namespace,
the <I>nested-name-specifier</I> shall not name any of the namespaces that
enclose the member's definition.
</BLOCKQUOTE>

This results in the following behavior:

<PRE>
    namespace N {
        namespace M {
            void f();
            void g();
        }
        void M::f(){}     // okay
        void N::M::g(){}  // error
    }
</PRE>

I was very surprised when this rule was pointed out to me.  The change
appears to have been introduced around the time of the first Santa
Cruz meeting, but I don't recall discussion of it and could not find a
motion related to it.

<P>Regardless of where it came from, I also can't understand why it is there.
Certainly it shouldn't matter <I>how</I> you name a given class or namespace.</P>

<P>For example, the standard permits:</P>

<PRE>
    namespace N {
        namespace M {
            void f();
            void g();
        }
        namespace X = M;
        namespace Y = N::M;
        void X::f(){}  // okay
        void Y::g(){}  // okay
    }
</PRE>

So, it is okay to use an alias for <TT>N::M</TT>,
but not to use <TT>N::M</TT> directly. 
Note that it <I>is</I> okay to use <TT>N::M</TT>
in any other context at this point
in the program (i.e., the rule is a specific restriction on declarator
names, not a general rule on the use of qualified names).

<P>Does anyone recall the intent of this rule or any rationale for its
existence?</P>

<P>
<B>Notes from 04/00 meeting:</B>
</P>

<P>There was some question as to whether this issue actually
constituted a defect in the Standard.  John Spicer suggested that
machine-generated source code would be likely to run afoul of this
prohibition.  Francis Glassborow expressed support for a rule that
would allow full qualification, or qualification relative to the
namespace containing the definition, but not qualification relative to
a containing namespace.  There was no consensus for moving forward
with a DR at this point, so the issue was left in "review" status.</P>

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>Remove the last sentence of
8.3&nbsp;



 <A HREF="decl.html#dcl.meaning">dcl.meaning</A> paragraph 1 (cited above) and the example
that follows.</P>

<BR>
<BR>
<HR>
<A NAME="135"></A>
<H4>135.
  
Class type in in-class member function definitions
</H4>
<B>Section: </B>8.3.5&nbsp;



 <A HREF="decl.html#dcl.fct">dcl.fct</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Gabriel Netterdag
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>1 July 1999<BR>





<P>3.2&nbsp;



 <A HREF="basic.html#basic.def.odr">basic.def.odr</A>
 paragraph 4 and
8.3.5&nbsp;



 <A HREF="decl.html#dcl.fct">dcl.fct</A>
 paragraph 6 indicate that
the return type and parameter types must be complete in a function
definition.  However, when
9.2&nbsp;



 <A HREF="class.html#class.mem">class.mem</A>
 paragraph 2 lists the
contexts in a class <I>member-specification</I> in which the class
is considered complete, the return type and parameter types of a
member function defined in the class definition are not included.
It thus appears that the following example is ill-formed:</P>

<PRE>
    struct S {
        S f() { return S(); }    // error: incomplete return type
        void g(S) { }            // error: incomplete parameter type
    };
</PRE>

<U>Jack Rouse</U>:
I suggest supplementing the text in 8.3.5p6 with something like:

<BLOCKQUOTE>
The type of a parameter or the return type for a function definition
shall not be an incomplete class type unless the function definition
is nested in the <I>member-specification</I> for that class (including
definitions in nested classes defined within the class).
</BLOCKQUOTE>

<P>
<B>Proposed resolution (10/00):</B> Replace the last sentence of
8.3.5&nbsp;



 <A HREF="decl.html#dcl.fct">dcl.fct</A>
 paragraph 6 with</P>
<BLOCKQUOTE>
The type of a parameter or the return type for a function definition
shall not be an incomplete class type (possibly cv-qualified) unless
the function definition is nested within the
<I>member-specification</I> for that class (including definitions in
nested classes defined within the class).
</BLOCKQUOTE>
<BR>
<BR>
<HR>
<A NAME="1"></A>
<H4>1.
  
What if two using-declarations refer to the same function but the declarations introduce different default-arguments?
</H4>
<B>Section: </B>8.3.6&nbsp;



 <A HREF="decl.html#dcl.fct.default">dcl.fct.default</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Bill Gibbons
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>unknown<BR>





<P>3.3&nbsp;



 <A HREF="basic.html#basic.scope">basic.scope</A>
 paragraph 4 says:</P>
<BLOCKQUOTE>
Given a set of declarations in a single declarative region, each of
which specifies the same unqualified name,
<UL>
<LI>
they shall all refer to the same entity, or all refer to functions ...
</LI>
</UL>
</BLOCKQUOTE>
8.3.6&nbsp;



 <A HREF="decl.html#dcl.fct.default">dcl.fct.default</A>
 paragraph 9 says:
<BLOCKQUOTE>When a declaration of a function is introduced by way of a
<I>using-declaration</I> (7.3.3&nbsp;



 <A HREF="dcl.html#namespace.udecl">namespace.udecl</A>),
any default argument information associated with the
declaration is imported as well.</BLOCKQUOTE>
This is not really clear regarding what happens in the following case:
<PRE>
    namespace A {
            extern "C" void f(int = 5);
    }
    namespace B {
            extern "C" void f(int = 7);
    }
     
    using A::f;
    using B::f;
     
    f(); // ???
</PRE>
<B>Proposed resolution (10/00):</B>

<P>Add the following at the end of 13.3.3&nbsp;



 <A HREF="over.html#over.match.best">over.match.best</A>:</P>

<BLOCKQUOTE>
If the best viable function resolves to a function for which
multiple declarations were found, and if at least two of these
declarations &mdash; or
the declarations they refer to in the case of
<I>using-declaration</I>s &mdash; specify
a default argument that made the function viable, the program is ill-formed.
[<I>Example:</I>
<BR>
<TT>&nbsp;&nbsp;&nbsp; namespace A {</TT>
<BR>
<TT>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; extern "C" void f(int = 5);</TT>
<BR>
<TT>&nbsp;&nbsp;&nbsp; }</TT>
<BR>
<TT>&nbsp;&nbsp;&nbsp; namespace B {</TT>
<BR>
<TT>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; extern "C" void f(int = 5);</TT>
<BR>
<TT>&nbsp;&nbsp;&nbsp; }</TT>
<P>
<TT>&nbsp;&nbsp;&nbsp; using A::f;</TT>
<BR>
<TT>&nbsp;&nbsp;&nbsp; using B::f;</TT>
</P>
<P>
<TT>&nbsp;&nbsp;&nbsp; void use() {</TT>
<BR>
<TT>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; f(3);&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
// OK, default argument was not used for viability</TT>
<BR>
<TT>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; f();&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
// Error: found default argument twice</TT>
<BR>
<TT>&nbsp;&nbsp;&nbsp; }</TT>
</P>
<P>&nbsp; &mdash;<I>end example</I>]</P>
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="65"></A>
<H4>65.
  
Typo in default argument example
</H4>
<B>Section: </B>8.3.6&nbsp;



 <A HREF="decl.html#dcl.fct.default">dcl.fct.default</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>6 Oct 1998<BR>



<P>
<B>Proposed Resolution (04/99):</B>
Change the text in the example of section 8.3.6&nbsp;



 <A HREF="decl.html#dcl.fct.default">dcl.fct.default</A>
 paragraph 5
from:</P>
<BLOCKQUOTE>... <TT>g</TT> will be called with the value <TT>f(1)</TT>.</BLOCKQUOTE>
to:
<BLOCKQUOTE>... <TT>g</TT> will be called with the value <TT>f(2)</TT>.</BLOCKQUOTE>
<BR>
<BR>
<HR>
<A NAME="217"></A>
<H4>217.
  
Default arguments for non-template member functions of class templates
</H4>
<B>Section: </B>8.3.6&nbsp;



 <A HREF="decl.html#dcl.fct.default">dcl.fct.default</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Martin Sebor
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>22 Mar 2000<BR>




<P>
According to 8.3.6&nbsp;



 <A HREF="decl.html#dcl.fct.default">dcl.fct.default</A> paragraphs 4 and 6,

<BLOCKQUOTE>

<P>For non-template functions, default arguments can be added in later
declarations of a function in the same scope.</P>

<P>The default arguments in a member function definition that appears
outside of the class definition are added to the set of default
arguments provided by the member function declaration in the class
definition.</P>

</BLOCKQUOTE>
</P>

<P>This would appear to allow the following example, in which a
default argument is added to a non-template member function of a class
template:</P>

<PRE>
    template &lt;class T&gt;
    struct S
    {
	void foo (int);
    };

    template &lt;class T&gt;
    void S&lt;T&gt;::foo (int = 0) { }
</PRE>

<P>
<U>John Spicer</U>:
The wording "non-template
functions" is somewhat unclear with respect to member functions of class
templates, but I know that this was intended to include them because it
originates from issue 3.13 of the template issues list that I maintained for
several years.</P>

<P>Having said that, the rationale for this restriction has since been made
obsolete, so this could (in theory) be changed in the standard if it is
problematic for users.</P>

<P>(See also <A HREF="
     cwg_active.html#205">issue 205</A>.)</P>

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>In 8.3.6&nbsp;



 <A HREF="decl.html#dcl.fct.default">dcl.fct.default</A> paragraph 6, replace</P>

<BLOCKQUOTE>

The default arguments in a member function definition that appears
outside of the class definition are added to the set of default
arguments provided by the member function declaration in the class
definition.

</BLOCKQUOTE>

<P>with</P>

<BLOCKQUOTE>

Except for member functions of class templates, the default arguments
in a member function definition that appears outside of the class
definition are added to the set of default arguments provided by the
member function declaration in the class definition.  Default
arguments for a member function of a class template must be specified
on the initial declaration of the member function within the class
template.

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="35"></A>
<H4>35.
  
Definition of default-initialization
</H4>
<B>Section: </B>8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Andrew Koenig
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>29 Jul 1998<BR>





<P>Given:</P>
<PRE>
    struct S1 {
        int x;
    };
    
    struct S2 {
        int x;
        double y;
    };
    
    struct S3 {
        int x;
        double y;
        string s;
    };
</PRE>
Once upon a time, we went through a fairly protracted discussion to ensure
that <TT>S1().x</TT> would be guaranteed to be 0. Note that if we declare
<PRE>
    void f()
    {
        S1 s1;
    
        // ...
    }
</PRE>
there is no guarantee of the value of <TT>s1.x</TT>, and that is intentional.
But <TT>S1().x</TT> is different, because <TT>S1()</TT> is an rvalue, and
unless all of its members are defined, the effect of copying it is undefined.

<P>Similarly, <TT>S2().x</TT> and <TT>S2().y</TT> are also defined to be
equal to zero, and here it really matters for many implementations, because
if <TT>S2().y</TT> is just a bunch of random bits, it is entirely possible
that trying to copy <TT>S2().y</TT> will yield a floating-point trap.</P>

<P>However, rather to my surprise, the standard does not define the value
of <TT>S3().x</TT> or <TT>S3().y</TT>, because <TT>S3</TT> is not a POD.
It does define <TT>S3().s</TT> (by running the string constructor), but
once a structure is no longer a POD, the values of uninitialized members
are no longer guaranteed in expressions of the form T().</P>

<P>In my opinion, this definition is a mistake, and the committee's intention
was to zero-initialize all members that do not have an explicitly defined
constructor, whether or not the class is a POD.</P>

<P>
See also paper J16/99-0014 = WG21 N1191.</P>

<P>
<I>[Note: this issue is resolved by the resolution of
<A HREF="
     cwg_defects.html#178">issue 178</A>.]</I>
</P>
<BR>
<BR>
<HR>
<A NAME="151"></A>
<H4>151.
  
Terminology of zero-initialization
</H4>
<B>Section: </B>8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Valentin Bonnard
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>4 August 1999<BR>



<P>In 3.6.2&nbsp;



 <A HREF="basic.html#basic.start.init">basic.start.init</A>
 paragraph 1 and
8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A>
 paragraphs 5 and 6, the
terms "memory" and "storage" are used in connection with
zero-initialization.  This is inaccurate; it is the variables that are
zero-initialized, not the storage.  (An all-zero bit pattern in the
storage may, in fact, not correspond to the representation of zero
converted to the appropriate type, and it is the latter that is being
described.)</P>

<P>Suggested resolution: remove the words "storage" and "memory" in
these contexts.</P>

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>
Delete the words "The storage for" from the first sentence of
3.6.2&nbsp;



 <A HREF="basic.html#basic.start.init">basic.start.init</A>
 paragraph 1.</P>

<P>
<I>[Note: Revised wording in 8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A>
relating to this issue is also found
in <A HREF="
     cwg_defects.html#178">issue 178</A>.]</I>
</P>
<BR>
<BR>
<HR>
<A NAME="178"></A>
<H4>178.
  
More on value-initialization
</H4>
<B>Section: </B>8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Andrew Koenig
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>25 Oct 1999<BR>



<P>When the Committee considered
<A HREF="
     cwg_defects.html#35">issue 35</A>, another context in which
value initialization might be relevant was overlooked:
<I>mem-initializer</I>s.  It would seem reasonable that if
<TT>T()</TT> as an expression invokes value initialization, that the
same syntactic construct in a <I>mem-initializer-list</I> would do the
same, and the usefulness of value initialization in that context is at
least as great as the standalone case.</P>

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>
<I>[Note: this resolution supersedes the resolution to
<A HREF="
     cwg_defects.html#35">issue 35</A>.]</I>
</P>

<P>In 5.2.3&nbsp;



 <A HREF="expr.html#expr.type.conv">expr.type.conv</A> paragraph 2, replace "whose value
is determined by default-initialization" by "which is
value-initialized".
</P>

<P>In 5.3.4&nbsp;



 <A HREF="expr.html#expr.new">expr.new</A> paragraph 15,</P>

<UL>

<LI>In the first subitem of the first item, restore the missing
period at the end of the first sentence.</LI>

<LI>In the second item, replace the text after the comma by
"the item is value-initialized (8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A>)".</LI>

</UL>

<P>Replace 8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A> paragraph 5 by:</P>

<BLOCKQUOTE>

<P>To <I>zero-initialize</I> an object of type <TT>T</TT> means:</P>

<UL>

<LI>if <TT>T</TT> is a scalar type (3.9&nbsp;



 <A HREF="basic.html#basic.types">basic.types</A>), the
object is set to the value of 0 (zero) converted to <TT>T</TT>;</LI>

<LI>if <TT>T</TT> is a non-union class type, each non-static data
member and each base-class subobject is zero-initialized;</LI>

<LI>if <TT>T</TT> is a union type, the object's first named data member
[<I>Footnote:</I> This member must not be <TT>static</TT>, by virtue
of the requirements in 9.5&nbsp;



 <A HREF="class.html#class.union">class.union</A>. <I>end
footnote</I>] is zero-initialized;</LI>

<LI>if <TT>T</TT> is an array type, each element is
zero-initialized;</LI>

<LI>if <TT>T</TT> is a reference type, no initialization is
performed.</LI>

</UL>

<P>To <I>default-initialize</I> an object of type <TT>T</TT> means:</P>

<UL>

<LI>if <TT>T</TT> is a non-POD class type (clause 9&nbsp;



 <A HREF="class.html#class">class</A>), the default constructor for <TT>T</TT> is called (and the
initialization is ill-formed if <TT>T</TT> has no accessible default
constructor);</LI>

<LI>if <TT>T</TT> is an array type, each element is
default-initialized;</LI>

<LI>otherwise, the object is zero-initialized.</LI>

</UL>

<P>To <I>value-initialize</I> an object of type <TT>T</TT> means: </P>

<UL>

<LI>if <TT>T</TT> is a class type (clause 9&nbsp;



 <A HREF="class.html#class">class</A>)
with a user-declared constructor (12.1&nbsp;



 <A HREF="special.html#class.ctor">class.ctor</A>), then
the default constructor for <TT>T</TT> is called (and the
initialization is ill-formed if <TT>T</TT> has no accessible default
constructor);</LI>

<LI>if <TT>T</TT> is a non-union class type without a user-declared
constructor, then every non-static data member and base-class
component of <TT>T</TT> is value-initialized;</LI>

<LI>if <TT>T</TT> is an array type, then each element is
value-initialized; </LI>

<LI>otherwise, the object is zero-initialized. </LI>

</UL>

<P>A program that calls for default-initialization of an entity of
reference type is ill-formed.  If <TT>T</TT> is a cv-qualified type,
the cv-unqualified version of <TT>T</TT> is used for these definitions
of zero-initialization, default-initialization, and
value-initialization.</P>

</BLOCKQUOTE>

<P>In 8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A> paragraph 6, change "The memory
occupied by any" to "Every".</P>


<P>In 8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A> paragraph 7, replace
"default-initialized" by "value-initialized".</P>


<P>In 8.5.1&nbsp;



 <A HREF="decl.html#dcl.init.aggr">dcl.init.aggr</A> paragraph 7, replace
"default-initialized" by "value-initialized".</P>


<P>In 12.3.1&nbsp;



 <A HREF="special.html#class.conv.ctor">class.conv.ctor</A> paragraph 2, insert "or
value-initialization" after the first occurrence of
"default-initialization".</P>


<P>In 12.6&nbsp;



 <A HREF="special.html#class.init">class.init</A> paragraph 1, replace the note by "The
object is default-initialized if there is no initializer, or
value-initialized if the initializer is <TT>()</TT>" [i.e., replace
the non-normative note by different, normative text].</P>


<P>In 12.6.1&nbsp;



 <A HREF="special.html#class.expl.init">class.expl.init</A> paragraph 2, replace
"default-initialized" by "value-initialized".</P>


<P>In 12.6.2&nbsp;



 <A HREF="special.html#class.base.init">class.base.init</A> paragraph 3, replace
"default-initialized" by "value-initialized" in the first bulleted
item.</P>

<P>In 12.6.2&nbsp;



 <A HREF="special.html#class.base.init">class.base.init</A> paragraph 4, replace
"default-initialized, nor initialized" by "default-initialized, nor
value-initialized, nor assigned".</P>

<BR>
<BR>
<HR>
<A NAME="304"></A>
<H4>304.
  
Value-initialization of a reference
</H4>
<B>Section: </B>8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Adamczyk
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>25 Jul 2001<BR>




<P>Another glitch in the TC1/<A HREF="
     cwg_defects.html#178">core issue 178</A>
definition of value-initialization:
it's no longer an error to value-initialize a reference.  That makes an example
like
<PRE>
typedef struct { int &amp;r; } S;
int main() {
  S();  // Error in C++98, okay in TC1!
}
</PRE>
valid, which has got to be wrong.  See 8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A> paragraph
5, where there is wording that forbids default-initialization of a
reference, but not value-initialization thereof. As noted in
<A HREF="
     cwg_defects.html#302">issue 302</A>, if
the default constructor were required to be generated when a
value-initialization is done, that would force an error.</P>

<P>
<B>Proposed resolution (10/01):</B>
</P>

<P>Add the indicated wording to the indicated sentence in
8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A> paragraph 5:</P>
<BLOCKQUOTE>
A program that calls for default-initialization <B>or value-initialization</B>
of an entity of reference type is ill-formed.
</BLOCKQUOTE>



<BR>
<BR>
<HR>
<A NAME="163"></A>
<H4>163.
  
Description of subaggregate initializer
</H4>
<B>Section: </B>8.5.1&nbsp;



 <A HREF="decl.html#dcl.init.aggr">dcl.init.aggr</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>12 Aug 1999<BR>



<P>8.5.1&nbsp;



 <A HREF="decl.html#dcl.init.aggr">dcl.init.aggr</A>
 paragraph 2 says,</P>

<BLOCKQUOTE>
When an aggregate is initialized the <I>initializer</I> can be an
<I>initializer-clause</I> consisting of a brace-enclosed,
comma-separated list of <I>initializer</I>s for the members of the
aggregate.
</BLOCKQUOTE>

Neither of these uses of the syntactic nonterminal <I>initializer</I>
corresponds to the grammar:

<UL>
<I>initializer</I>:
<UL>
<TT>=</TT> <I>initializer-clause</I>
</UL>
<UL>
<TT>(</TT> <I>expression-list</I> <TT>)</TT>
</UL>
</UL>

<P>
<B>Proposed resolution (10/99):</B> replace the quoted words with:</P>

<BLOCKQUOTE>
When an aggregate is initialized the <I>initializer</I> can
<B>contain</B> an <I>initializer-clause</I> consisting of a
brace-enclosed, comma-separated list of
<B><I>initializer-clause</I>s</B> for the members of the aggregate.
</BLOCKQUOTE>
<BR>
<BR>
<HR>
<A NAME="148"></A>
<H4>148.
  
POD classes and pointers to members
</H4>
<B>Section: </B>9&nbsp;



 <A HREF="class.html#class">class</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Nathan Sidwell
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>31 Jul 1999<BR>



<P>3.9&nbsp;



 <A HREF="basic.html#basic.types">basic.types</A>
 paragraph 10
defines pointer to member types to be scalar types. It
also defines scalar types to be one of the POD types.</P>

<P>9&nbsp;



 <A HREF="class.html#class">class</A>
 paragraph 4
defines a POD struct as an aggregate class with no non-static data
members of type pointer to member.</P>

<P>It seems contradictory that a type can be POD,
yet a class containing that type
is non-POD.</P>

<P>Suggested resolution:
Alter 9&nbsp;



 <A HREF="class.html#class">class</A>
 paragraph 4
to allow pointer to member objects as non-static data members of POD
class.</P>

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>In 9&nbsp;



 <A HREF="class.html#class">class</A> paragraph 4, remove all occurrences of
"pointer to member."</P>
<BR>
<BR>
<HR>
<A NAME="176"></A>
<H4>176.
  
Name injection and templates
</H4>
<B>Section: </B>9&nbsp;



 <A HREF="class.html#class">class</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>John Spicer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>21 February 1999<BR>



<P>There is some controversy about whether class name injection applies
to class templates.  If it does apply, what is injected?  Is a class
name injected or is the thing that is injected actually a template?</P>

<P>Clause 9&nbsp;



 <A HREF="class.html#class">class</A>
 paragraph 2 says,</P>
<BLOCKQUOTE>
The <I>class-name</I> is also inserted into the scope of the class
itself.
</BLOCKQUOTE>

In general, clause 9 applies to both classes and class templates, so I
would take this to mean that class name imjection does indeed apply to
class templates.  One problem with this is that clause 9 uses the
syntactic term <I>class-name</I>, which I would take to imply that the
inserted name is always a class.  This is clearly unacceptable for
class templates as it makes the template itself unusable from with the
template.  For example:

<PRE>
    template &lt;class T&gt; struct A {
        A&lt;T*&gt; ptr;    // Invalid: A refers to a class
    };
</PRE>

<P>Clearly the injected name must be usable as both a class and a
class template.  This kind of magic already exists in the standard.
In 14.6.1&nbsp;



 <A HREF="template.html#temp.local">temp.local</A>
 it says,</P>

<BLOCKQUOTE>
Within the scope of a class template, when the name of the template is
neither qualified nor followed by <TT>&lt;</TT>, it is equivalent to
the name of the template followed by the
<I>template-parameter</I>s enclosed in &lt;&gt;.
</BLOCKQUOTE>

<P>The proposal here is that we clarify that name injection does
indeed apply to class templates, and that it is the injected name that
has the special property of being usable as both a class and a
template name (as described in
14.6.1&nbsp;



 <A HREF="template.html#temp.local">temp.local</A>
).  This would eliminate
the need for special wording regarding the qualification of the name,
but would achieve the same result.  This would also make this
"special" name available to a derived class of a class template
&mdash; something which is necessary if the benefits of class name
injection are to be made uniformly available for class templates, too.</P>

<PRE>
    template &lt;class T&gt; struct Base {
        Base* p;
        Base&lt;T*&gt;* p2;
        ::Base* p3;    // Error: only injected name usable as class
    };

    template &lt;class T&gt; struct Derived: public Base&lt;T&gt; {
        Base* p;    // Now okay
        Base&lt;T*&gt;* p2;    // Still okay
        Derived::Base* p3;    // Now okay
</PRE>

Note that by giving the special attribute of being usable as both a
class and a template to the injected name it is now clear where this
attribute can and cannot be used.

<P>(See paper J16/99-0010 = WG21 N1187.)</P>

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>
<I>[Note: these changes depend on the resolution for <A HREF="
     cwg_defects.html#147">issue 147</A>.]</I>
</P>

<P>Replace 14.6.1&nbsp;



 <A HREF="template.html#temp.local">temp.local</A> paragraphs 1 and 2 with the
following:</P>

<BLOCKQUOTE>

<P>Like normal (non-template) classes, class templates have an
injected-class-name (clause 9&nbsp;



 <A HREF="class.html#class">class</A>).  The
injected-class-name can be used with or without a
<I>template-argument-list</I>.  When it is used without a
<I>template-argument-list</I>, it is equivalent to the
injected-class-name followed by the <I>template-parameter</I>s of the
class template enclosed in <TT>&lt;&gt;</TT>.  When it is used with a
<I>template-argument-list</I>, it refers to the specified class
template specialization, which could be the current specialization or
another specialization.</P>

<P>Within the scope of a class template specialization or partial
specialization, when the injected-class-name is not followed by a
<TT>&lt;</TT>, it is equivalent to the injected-class-name followed by
the <I>template-argument</I>s of the class template specialization or
partial specialization enclosed in <TT>&lt;&gt;</TT>.
[<I>Example:</I>
</P>

<PRE>
    template&lt;class T&gt; class Y;
    template&lt;&gt; class Y&lt;int&gt; {
        Y* p;          // <I>meaning</I> Y&lt;int&gt;
        Y&lt;char&gt;* q;    // <I>meaning</I> Y&lt;char&gt;
    };
</PRE>

<P>&mdash;<I>end example</I>]</P>

<P>The injected-class-name of a class template or class template
specialization can be used either with or without a
<I>template-argument-list</I> wherever it is in scope.
[<I>Example:</I>
</P>

<PRE>
    template &lt;class T&gt; struct Base {
        Base* p;
    };

    template &lt;class T&gt; struct Derived: public Base&lt;T&gt; {
        typename Derived::Base* p;  // <I>meaning</I> Derived::Base&lt;T&gt;
    };
</PRE>

<P>&mdash;<I>end example</I>]</P>

<P>A lookup that finds an injected-class-name (10.2&nbsp;



 <A HREF="derived.html#class.member.lookup">class.member.lookup</A>) can result in an ambiguity in certain cases (for
example, if it is found in more than one base class).  If all of the
injected-class-names that are found refer to specializations of the
same class template, and if the name is followed by a
<I>template-argument-list</I>, the reference refers to the class
template itself and not a specialization thereof, and is not
ambiguous.  [<I>Example:</I>
</P>

<PRE>
    template &lt;class T&gt; struct Base { };
    template &lt;class T&gt; struct Derived: Base&lt;int&gt;, Base&lt;char&gt; {
        typename Derived::Base b;            // <I>error: ambiguous</I>
        typename Derived::Base&lt;double&gt; d;    // <I>OK</I>
    };
</PRE>

<P>&mdash;<I>end example</I>]</P>

<P>When the normal name of the template (i.e., the name from the
enclosing scope, not the injected-class-name) is used without a
<I>template-argument-list</I>, it refers to the class template itself
and not a specialization of the template.  [<I>Example:</I>
</P>

<PRE>
    template &lt;class T&gt; class X {
        X* p;         // <I>meaning</I> X&lt;T&gt;
        X&lt;T&gt;* p2;
        X&lt;int&gt;* p3;
        ::X* p4;      // <I>error: missing template argument list</I>
                      // ::X <I>does not refer to the injected-class-name</I>
    };
</PRE>

<P>&mdash;<I>end example</I>]</P>

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="75"></A>
<H4>75.
  
In-class initialized members must be const
</H4>
<B>Section: </B>9.2&nbsp;



 <A HREF="class.html#class.mem">class.mem</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>John Wiegley
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>29 Dec 1998<BR>





<P>The standard says, in
9.2&nbsp;



 <A HREF="class.html#class.mem">class.mem</A>

paragraph 4:</P>
<BLOCKQUOTE>A <I>member-declarator</I> can contain a
<I>constant-initializer</I> only
if it declares a <TT>static</TT> member
(9.4&nbsp;



 <A HREF="class.html#class.static">class.static</A>
)
of integral or enumeration type, see
9.4.2&nbsp;



 <A HREF="class.html#class.static.data">class.static.data</A>
.</BLOCKQUOTE>
But later, in the section on static class data member initialization,
9.4.2&nbsp;



 <A HREF="class.html#class.static.data">class.static.data</A>

paragraph 4, it says:
<BLOCKQUOTE>
If a <TT>static</TT> data member is of <TT>const</TT> integral
or <TT>const</TT> enumeration
type, its declaration in the class definition can specify a
<I>constant-initializer</I> which shall be an integral constant expression
(5.19&nbsp;



 <A HREF="expr.html#expr.const">expr.const</A>
). In that case, the
member can appear in integral constant expressions within its scope.
</BLOCKQUOTE>
The first paragraph should be modified to make it clear that it is not possible
to initialize a static data member in-line with a constant-initializer if that
data member is of integral (or enumeration) type, and yet not const.

<P>
<B>Proposed Resolution (10/99):</B>
Change the sentence in 9.2&nbsp;



 <A HREF="class.html#class.mem">class.mem</A>
 paragraph 4 to read:</P>
<BLOCKQUOTE>
A <I>member-declarator</I> can contain a <I>constant-initializer</I>
only if it declares a <TT>static</TT> member
(9.4&nbsp;



 <A HREF="class.html#class.static">class.static</A>
)
of <TT>const</TT> integral or <TT>const</TT> enumeration type,
see 9.4.2&nbsp;



 <A HREF="class.html#class.static.data">class.static.data</A>
.
</BLOCKQUOTE>
<BR>
<BR>
<HR>
<A NAME="80"></A>
<H4>80.
  
Class members with same name as class
</H4>
<B>Section: </B>9.2&nbsp;



 <A HREF="class.html#class.mem">class.mem</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Jason Merrill
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>5 Dec 1998<BR>





<P>Between the May '96 and September '96 working papers, the text in
9.2&nbsp;



 <A HREF="class.html#class.mem">class.mem</A>

paragraph 13:</P>
<BLOCKQUOTE>If <TT>T</TT> is the name of a class, then each of the following
shall have a name different from <TT>T</TT>:
<UL>
<LI>
every static data member of class <TT>T</TT>;</LI>
</UL>
</BLOCKQUOTE>
was changed by removing the word 'static'. Looking over the meeting
minutes from Stockholm, none of the proposals seem to include this
change, which breaks C compatibility and is not mentioned in the compatibility
annex. Was this change actually voted in by the committee?

<P>Specifically, this breaks <TT>/usr/include/netinet/in.h</TT> under Linux,
in which "<TT>struct ip_opts</TT>" shares its name with one of its members.</P>

<P>
<B>Proposed resolution (10/00):</B>
</P>
<OL>
<LI>
Change the first bullet of
9.2&nbsp;



 <A HREF="class.html#class.mem">class.mem</A>
 paragraph 13 to say
<UL>
<LI>
every static data member of class <TT>T</TT>;</LI>
</UL>
<LI>
Add another paragraph before
9.2&nbsp;



 <A HREF="class.html#class.mem">class.mem</A>
 paragraph 14, reading
<BLOCKQUOTE>
In addition, if class <TT>T</TT> has a user-declared constructor
(12.1&nbsp;



 <A HREF="special.html#class.ctor">class.ctor</A>
), every nonstatic
data member of class <TT>T</TT> shall have a name different from
<TT>T</TT>.
</BLOCKQUOTE>
</LI>
</LI>
</OL>
<BR>
<BR>
<HR>
<A NAME="190"></A>
<H4>190.
  
Layout-compatible POD-struct types
</H4>
<B>Section: </B>9.2&nbsp;



 <A HREF="class.html#class.mem">class.mem</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Adamczyk
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>20 Dec 1999<BR>





<P>The definition of layout-compatible POD-struct types in
9.2&nbsp;



 <A HREF="class.html#class.mem">class.mem</A>
 paragraph 14 requires that
the two types</P>

<BLOCKQUOTE>
have the same number of members, and corresponding members (in order)
have layout-compatible types (3.9).
</BLOCKQUOTE>

There does not appear to be any reason for including member functions
and static data members in this requirement.  It would be more logical
to require only that the non-static data members of the two types must
match.

<P>The characteristics of layout-compatible types are not well
described in the current wording, either.  Apart from their use in
9.2&nbsp;



 <A HREF="class.html#class.mem">class.mem</A>
 paragraph 16 to define the
term "common initial sequence," there appears to be nothing said about
which operations are possible between objects of layout-compatible types.
For example, 3.9&nbsp;



 <A HREF="basic.html#basic.types">basic.types</A>
 paragraphs
2-3 give certain guarantees regarding use of <TT>memcpy</TT> on
objects of the same type; it might be reasonable to assume that the
same kinds of guarantees might apply to objects of layout-compatible
types, but that is not said.  Similarly,
3.10&nbsp;



 <A HREF="basic.html#basic.lval">basic.lval</A>
 paragraph 15 describes
permissible "type punning" but does not mention layout-compatible types.</P>

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>In 9.2&nbsp;



 <A HREF="class.html#class.mem">class.mem</A> paragraphs 14 and 15, change all
occurrences of "members" to "nonstatic data members."</P>
<BR>
<BR>
<HR>
<A NAME="67"></A>
<H4>67.
  
Evaluation of left side of object-expression
</H4>
<B>Section: </B>9.4&nbsp;



 <A HREF="class.html#class.static">class.static</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>6 Oct 1998<BR>



<P>Paragraph 2 says that "the object-expression is always evaluated" when
the class member syntax is used to refer to a static member. This
presumably should say that the object expression is evaluated if the member
access is performed, i.e., not if the overall expression is the operand
of <TT>sizeof</TT> or the unevaluated branch of <TT>?:</TT>, <TT>||</TT>, or <TT>&amp;&amp;</TT>.</P>

<P>
<B>Proposed Resolution (10/99):</B>
Replace "is always evaluated" by "is evaluated" in
9.4&nbsp;



 <A HREF="class.html#class.static">class.static</A>
 paragraph 2.</P>
<BR>
<BR>
<HR>
<A NAME="48"></A>
<H4>48.
  
Definitions of unused static members
</H4>
<B>Section: </B>9.4.2&nbsp;



 <A HREF="class.html#class.static.data">class.static.data</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Bill Gibbons
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>23 Nov 1997<BR>



<P>Also see section: 3.2&nbsp;



 <A HREF="basic.html#basic.def.odr">basic.def.odr</A>
.</P>

<P>Originally, all static data members still had to be defined outside the
class whether they were used or not.</P>

<P>But that restriction was supposed to be lifted so that static
data members need not be defined outside the class unless they are used
in a manner which requires their definition,
in the same manner as namespace-scope
variables. In particular, if an integral/enum const static data member
is initialized within the class, and its address is never taken, we agreed
that no namespace-scope definition was required.</P>

<P>For example:</P>
<PRE>
    struct A {
        static const int size = 10;
        int array[size];
    };
    
    int main() {
        A a;
        return 0;
    }
</PRE>
However, 9.4.2&nbsp;



 <A HREF="class.html#class.static.data">class.static.data</A>
 paragraph 4 says:
<BLOCKQUOTE>The member shall still be defined in a namespace scope if it
is used in the program and the namespace scope definition shall not contain
an initializer.</BLOCKQUOTE>
A narrow interpreration of "used" in this rule would make the example ill-formed
because there is no namespace-scope definition of "<TT>size</TT>".
A better wording for this rule would be:
<BLOCKQUOTE>The member shall still be defined in a namespace scope if it
is used in the program in the manner described in 3.2&nbsp;



 <A HREF="basic.html#basic.def.odr">basic.def.odr</A>
.
The namespace scope definition shall not contain an initializer.</BLOCKQUOTE>
Also, the wording in 3.2&nbsp;



 <A HREF="basic.html#basic.def.odr">basic.def.odr</A>
 paragraph 2:
<BLOCKQUOTE>An expression is potentially evaluated unless either it is
the operand of the <TT>sizeof</TT> operator (5.3.3&nbsp;



 <A HREF="expr.html#expr.sizeof">expr.sizeof</A>
), or it is the operand
of the <TT>typeid</TT> operator and does not designate an lvalue of polymorphic
class type (5.2.8&nbsp;



 <A HREF="expr.html#expr.typeid">expr.typeid</A>
).</BLOCKQUOTE>
is incomplete because it does not mention the use of a compile-time constant
as an array bound or template argument. It should say something like:
<BLOCKQUOTE>An expression is potentially evaluated unless it is the operand
of the sizeof operator (5.3.3&nbsp;



 <A HREF="expr.html#expr.sizeof">expr.sizeof</A>
), the operand of the typeid operator,
<U>an <I>integral constant-expression</I> used as an array bound or an
<I>integral constant-expression</I> used as a <I>template-argument</I>
for a non-reference <I>template-parameter</I></U>; and the expression
does not designate an lvalue of polymorphic class type (5.2.8&nbsp;



 <A HREF="expr.html#expr.typeid">expr.typeid</A>
).</BLOCKQUOTE>

<P>
<B>Proposed Resolution (04/99):</B>
Change the first sentence of 3.2&nbsp;



 <A HREF="basic.html#basic.def.odr">basic.def.odr</A>

paragraph 2 from:</P>
<BLOCKQUOTE>An expression is <I>potentially evaluated</I> unless either
it is the operand of the <TT>sizeof</TT> operator (5.3.3&nbsp;



 <A HREF="expr.html#expr.sizeof">expr.sizeof</A>
), or it is the
operand of the <TT>typeid</TT> operator and does not designate an lvalue
of polymorphic class type (5.2.8&nbsp;



 <A HREF="expr.html#expr.typeid">expr.typeid</A>
).</BLOCKQUOTE>
to:
<BLOCKQUOTE>An expression is <I>potentially evaluated</I> unless <U>it
appears where an <I>integral constant expression</I> is required (see 5.19&nbsp;



 <A HREF="expr.html#expr.const">expr.const</A>
),
is
</U>the operand of the <TT>sizeof</TT> operator (5.3.3&nbsp;



 <A HREF="expr.html#expr.sizeof">expr.sizeof</A>
), or
is the operand of the <TT>typeid</TT> operator and the expression does
not designate an lvalue of polymorphic class type (5.2.8&nbsp;



 <A HREF="expr.html#expr.typeid">expr.typeid</A>
).</BLOCKQUOTE>
<BR>
<BR>
<HR>
<A NAME="142"></A>
<H4>142.
  
Injection-related errors in access example
</H4>
<B>Section: </B>11.2&nbsp;



 <A HREF="access.html#class.access.base">class.access.base</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Adamczyk
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>16 Jul 1999<BR>





<P>In the example in paragraph 3 of
11.2&nbsp;



 <A HREF="access.html#class.access.base">class.access.base</A>
, all the references
to <TT>B</TT> in <TT>DD::f()</TT> should be replaced by <TT>::B</TT>.
The reason is that the class name <TT>B</TT> is private in <TT>D</TT>
and thus inaccessible in <TT>DD</TT>.  (The example was probably not
updated when class name injection was added.)</P>

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>Replace the example in
11.2&nbsp;



 <A HREF="access.html#class.access.base">class.access.base</A>
 paragraph 3 with:</P>
<PRE>
    class B {
    public:
        int mi;                 // nonstatic member
        static int si;          // static member
    };
    class D: private B {
    };
    class DD: public D {
        void f();
    };
    void DD::f() {
        mi = 3;                 // error: mi is private in D
        si = 3;                 // error: si is private in D
        ::B b;
        b.mi = 3;               // OK (b.mi is different from this-&gt;mi)
        b.si = 3;               // OK (b.si is different from this-&gt;si)
        ::B::si = 3;            // OK
        ::B* bp1 = this;        // error: B is a private base class
        ::B* bp2 = (::B*)this;  // OK with cast
        bp2-&gt;mi = 3;            // OK: access through a pointer to B
    }
</PRE>
<BR>
<BR>
<HR>
<A NAME="161"></A>
<H4>161.
  
Access to protected nested type
</H4>
<B>Section: </B>11.5&nbsp;



 <A HREF="access.html#class.protected">class.protected</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Adamczyk
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>26 Aug 1999<BR>



<P>11.5&nbsp;



 <A HREF="access.html#class.protected">class.protected</A>
 paragraph 1 begins:</P>

<BLOCKQUOTE>
When a friend or a member function of a derived class references a
protected nonstatic member of a base class, an access check applies in
addition to those described earlier in clause
11&nbsp;



 <A HREF="access.html#class.access">class.access</A>
.
</BLOCKQUOTE>

<P>This was intended to refer to nonstatic member functions and
nonstatic data members.  However, a protected nested type declared
in a base class is, by
some definition of the word, a "nonstatic" member, and therefore subject
to this additional access check.</P>

<P>
<B>Proposed resolution (10/99):</B>
change "protected nonstatic member" in the above to
"protected nonstatic member function or protected nonstatic data member"
to make the intent clear.</P>
<BR>
<BR>
<HR>
<A NAME="194"></A>
<H4>194.
  
Identifying constructors
</H4>
<B>Section: </B>12.1&nbsp;



 <A HREF="special.html#class.ctor">class.ctor</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Jamie Schmeiser
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>11 Jan 2000<BR>





<P>According to 12.1&nbsp;



 <A HREF="special.html#class.ctor">class.ctor</A>
 paragraph
1, the syntax used in declaring a constructor allows at most one
<I>function-specifier</I>.  It is thus not permitted to declare a
constructor both <TT>inline</TT> and <TT>explicit</TT>.  This seems
overly restrictive.</P>

<P>On a related note, there doesn't seem to be any explicit
prohibition against member functions with the same name as the class.
(Such a prohibition might reasonably be expected to occur in
9.2&nbsp;



 <A HREF="class.html#class.mem">class.mem</A>
 paragraph 13, but member
functions are not listed there.)</P>

<P>One possible interpretation would be that such member functions
would violate the restrictions in
3.3.6&nbsp;



 <A HREF="basic.html#basic.scope.class">basic.scope.class</A>
 paragraph 1,
because the class name would refer to the class at some points in the
class scope and to the member function at others.  However, this seems
a bit tenuous.  Is an explicit prohibition needed?</P>

<P>(See also <A HREF="
     cwg_defects.html#147">issue 147</A>.)</P>

<P>
<B>Proposed resolution (10/00):</B>
</P>

<OL>
<LI>
<P>Add to 9.2&nbsp;



 <A HREF="class.html#class.mem">class.mem</A> paragraph 13</P>

<BLOCKQUOTE>
<UL>
<LI>every member function of class <TT>T</TT> [<I>Note:</I> this
restriction does not apply to constructors, which do not have names
(12.1&nbsp;



 <A HREF="special.html#class.ctor">class.ctor</A>). ];</LI>
</UL>
</BLOCKQUOTE>

<P>immediately following the line</P>

<BLOCKQUOTE>
<UL>
<LI>every data member of class <TT>T</TT>;</LI>
</UL>
</BLOCKQUOTE>
</LI>

<LI>
<P>Change 12.1&nbsp;



 <A HREF="special.html#class.ctor">class.ctor</A> paragraph 1 from</P>

<BLOCKQUOTE>
A special declarator syntax using an optional
<I>function-specifier</I> (7.1.2&nbsp;



 <A HREF="dcl.html#dcl.fct.spec">dcl.fct.spec</A>)...
</BLOCKQUOTE>

<P>to</P>

<BLOCKQUOTE>
A special declarator syntax using an optional sequence of
<I>function-specifier</I>s (7.1.2&nbsp;



 <A HREF="dcl.html#dcl.fct.spec">dcl.fct.spec</A>)...
</BLOCKQUOTE>
</LI>
</OL>
<BR>
<BR>
<HR>
<A NAME="152"></A>
<H4>152.
  
<TT>explicit</TT> copy constructors
</H4>
<B>Section: </B>12.3.1&nbsp;



 <A HREF="special.html#class.conv.ctor">class.conv.ctor</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Adamczyk
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>4 August 1999<BR>





<P>Can a copy-constructor declared as <TT>explicit</TT> be used to
copy class values implicitly?  For example,</P>

<PRE>
   struct X {
      X();
      explicit X(const X&amp;);
   };
   void f(X);
   int main() { X x; f(x); }
</PRE>

According to 12.3.1&nbsp;



 <A HREF="special.html#class.conv.ctor">class.conv.ctor</A>

paragraphs 2-3,

<BLOCKQUOTE>
An explicit constructor constructs objects just like non-explicit
constructors, but does so only where the direct-initialization syntax
(8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A>
) or where casts
(5.2.9&nbsp;



 <A HREF="expr.html#expr.static.cast">expr.static.cast</A>
,
5.4&nbsp;



 <A HREF="expr.html#expr.cast">expr.cast</A>
) are explicitly used...
A copy-constructor (12.8&nbsp;



 <A HREF="special.html#class.copy">class.copy</A>
) is a
converting constructor.  An implicitly-declared copy constructor is
not an explicit constructor; it may be called for implicit type
conversions.
</BLOCKQUOTE>

This passage would appear to indicate that the call in the example is
ill-formed, since it uses neither the direct-initialization syntax nor
an explicit cast.  The last sentences are especially interesting in
this regard, indicating that <TT>explicit</TT> and
non-<TT>explicit</TT> copy constructors are handled differently.

<P>On the other hand,
8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A>
 paragraph 14, bullet 4,
sub-bullet 2 says,</P>

<BLOCKQUOTE>
If the initialization is direct-initialization, or if it is
copy-initialization where the cv-unqualified version of the source
type is the same class as, or a derived class of, the class of the
destination... [the] applicable constructors are enumerated
(13.3.1.3&nbsp;



 <A HREF="over.html#over.match.ctor">over.match.ctor</A>
)...
</BLOCKQUOTE>

The cited passage says that

<BLOCKQUOTE>
The candidate functions are all the constructors of the class of the
object being initialized.
</BLOCKQUOTE>

<P>
<B>Notes from 04/01 meeting:</B>
</P>

<P>After the issue was accepted as a DR with the proposed
resolution to change 13.3.1.3&nbsp;



 <A HREF="over.html#over.match.ctor">over.match.ctor</A> paragraph 1
as described below, it was noticed that 12.3.1&nbsp;



 <A HREF="special.html#class.conv.ctor">class.conv.ctor</A>
paragraph 3 states that:</P>

<BLOCKQUOTE>

A copy-constructor (12.8&nbsp;



 <A HREF="special.html#class.copy">class.copy</A>) is a converting
constructor.

</BLOCKQUOTE>

<P>In addition to making the proposed resolution for this issue
ineffectual, the wording of paragraph 3 also contradicts that of
paragraph 1:</P>

<BLOCKQUOTE>

A constructor declared without the <I>function-specifier</I>
<TT>explicit</TT> that can be called with a single parameter specifies
a conversion from the type of its first parameter to the type of its
class. Such a constructor is called a converting constructor.

</BLOCKQUOTE>

<P>These considerations led to the addition of the second point
of the proposed resolution.</P>

<P>
<B>Proposed resolution (04/01):</B>
</P>
<OL>
<LI>
<P>Change the first two sentences of
13.3.1.3&nbsp;



 <A HREF="over.html#over.match.ctor">over.match.ctor</A>
 paragraph 1 to</P>
<BLOCKQUOTE>
When objects of class type are direct-initialized
(8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A>), or copy-initialized
from an expression of the same or a derived class type
(8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A>), overload
resolution selects the constructor.  For direct-initialization, the
candidate functions are all the constructors of the class of the object
being initialized.  For copy-initialization, the candidate functions are
all the converting constructors
(12.3.1&nbsp;



 <A HREF="special.html#class.conv.ctor">class.conv.ctor</A>
) of that class.
</BLOCKQUOTE>
</LI>

<LI>
<P>Change the first sentence of 12.3.1&nbsp;



 <A HREF="special.html#class.conv.ctor">class.conv.ctor</A>
paragraph 3 to read:</P>

<BLOCKQUOTE>

A non-explicit copy constructor (12.8&nbsp;



 <A HREF="special.html#class.copy">class.copy</A>) is a
converting constructor.

</BLOCKQUOTE>
</LI>
</OL>
<BR>
<BR>
<HR>
<A NAME="193"></A>
<H4>193.
  
Order of destruction of local automatics of destructor
</H4>
<B>Section: </B>12.4&nbsp;



 <A HREF="special.html#class.dtor">class.dtor</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Gerhard Menzl
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>7 Jan 2000<BR>



<P>The Standard is not clear whether automatic objects in a destructor
are destroyed before or after the destruction of the class's base and
member subobjects.  That is, given</P>

<PRE>
    struct S { ~S(); };

    struct T {
        S x;
        ~T() {
            S y;
        };
    };
</PRE>

<P>which will be destroyed first, <TT>x</TT> or <TT>y</TT>?</P>

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>In 12.4&nbsp;



 <A HREF="special.html#class.dtor">class.dtor</A> paragraph 6, change

<BLOCKQUOTE>
A destructor for class <TT>X</TT> calls the destructors for
<TT>X</TT>'s direct members, ...
</BLOCKQUOTE>

to

<BLOCKQUOTE>
After executing the body of the destructor and destroying any
automatic objects allocated within the body, a destructor for class
<TT>X</TT> calls the destructors for <TT>X</TT>'s direct members, ...
</BLOCKQUOTE>
</P>
<BR>
<BR>
<HR>
<A NAME="235"></A>
<H4>235.
  
Assignment vs initialization
</H4>
<B>Section: </B>12.6.2&nbsp;



 <A HREF="special.html#class.base.init">class.base.init</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>16 Sep 2000<BR>


<P>In 12.6.2&nbsp;



 <A HREF="special.html#class.base.init">class.base.init</A> paragraph 4 we read:</P>

<BLOCKQUOTE>

After the call to a constructor for class <TT>X</TT> has completed, if
a member of <TT>X</TT> is neither specified in the constructor's
<I>mem-initializer</I>s, nor default-initialized, nor initialized
during execution of the body of the constructor, the member has
indeterminate value.

</BLOCKQUOTE>

<P>Using the term "initialized" to describe setting the value of a
member inside the body of a constructor is a misuse of the term: only
by use of a placement <TT>new</TT> expression can a member be
<I>initialized</I> "during the execution of the body of the
constructor."</P>

<P>
<B>Suggested resolution:</B> Change "initialized" to "given a
value."</P>

<P>
<B>Proposed resolution (10/00):</B> As suggested.</P>

<BR>
<BR>
<HR>
<A NAME="20"></A>
<H4>20.
  
Some clarifications needed for 12.8 para 15
</H4>
<B>Section: </B>12.8&nbsp;



 <A HREF="special.html#class.copy">class.copy</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>unknown
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>unknown<BR>





<P>
<B><U>Issue 1</U></B>
</P>

<P>12.8&nbsp;



 <A HREF="special.html#class.copy">class.copy</A>


(From J16/99-0005 = WG21 N1182, "Proposed Resolutions for Core
Language Issues 6, 14, 20, 40, and 89")</P>

<P>There are three related sub-issues in this issue, all dealing with the
elision of copy constructors as described in
12.8&nbsp;



 <A HREF="special.html#class.copy">class.copy</A>

paragraph 15:</P>
<OL>
<LI>
The text should make clear that the requirement that the copy constructor
be accessible and unambiguous is not relaxed in cases where a call to a
copy constructor is elided.</LI>

<LI>
It is not clear from the text that the two optimizations described can
be applied transitively, and, if so, the implications for the order of
destruction are not spelled out.</LI>

<LI>
The text should exclude applying the function-return optimization if the
expression names a static or volatile local object.</LI>
</OL>
<U>Analysis</U>

<P>After discussion in Santa Cruz, the core group decided that sub-issue
#1 required no change; the necessity of an accessible and unambiguous copy
constructor is made clear in
12.2&nbsp;



 <A HREF="special.html#class.temporary">class.temporary</A>

paragraph 1 and need not be repeated in this text. The remaining two sub-issues
appear to be valid criticisms and should be addressed.</P>

<P>
<B>Proposed Resolution (10/99):</B>
</P>

<P>
<I>[Note: a small portion of this wording is superseded by the
resolution of <A HREF="
     cwg_defects.html#185">issue 185</A>.]</I>
</P>

<P>The paragraph in question should be rewritten as follows.
In addition,
references to this section should be added to the index under "temporary,
elimination of," "elimination of temporary," and "copy, constructor elision."</P>
<UL>When certain criteria are met, an implementation is allowed to omit
the copy construction of a class object, even if the copy constructor
and/or destructor
for the object have side effects. In such cases, the implementation treats
the source and target of the omitted copy operation as simply two different
ways of referring to the same object, and the destruction of that object
occurs at the later of the times when the two objects would have been destroyed
without the optimization [<I>footnote:</I> Because only one object is destroyed
instead of two, and one copy constructor is not executed, there is still
one object destroyed for each one constructed. <I>end footnote</I>].
This elision
of copy operations is permitted in the following circumstances (which may
be combined to eliminate multiple copies):
<BR>
<UL>
<LI>
<P>in a return statement in a function with a class return type, where the
expression is the name of a non-volatile automatic object with the same
cv-unqualified type as the function return type, the copy operation can
be omitted by constructing the automatic object directly into the function's
return value</P>
</LI>
</UL>
</UL>

<UL>
<UL>
<LI>
when a temporary class object 
(12.2&nbsp;



 <A HREF="special.html#class.temporary">class.temporary</A>
)
would be copied to a class object with the same cv-unqualified type,
the copy operation can be omitted by constructing the temporary object
directly into the target of the omitted copy</LI>
</UL>
</UL>

<UL>[<I>Example:</I>
</UL>

<UL>
<PRE>
    class Thing {
    public:
        Thing();
        ~Thing();
        Thing(const Thing&amp;);
    };
    
    Thing f() {
        Thing t;
        return t;
    }
    
    Thing t2 = f();
</PRE>
</UL>
Here the criteria for elision can be combined to eliminate two calls to
the copy constructor of class <TT>Thing</TT>: the copying of the local
automatic object <TT>t</TT> into the temporary object for the return value
of function <TT>f()</TT> and the copying of that temporary object into
object <TT>t2</TT>. Effectively, the construction of the local object <TT>t</TT>
can be viewed as directly initializing the global object <TT>t2</TT>, and
that object's destruction will occur at program exit.
&mdash;<I>end example</I>]
<BR>
<BR>
<HR>
<A NAME="185"></A>
<H4>185.
  
"Named" temporaries and copy elision
</H4>
<B>Section: </B>12.8&nbsp;



 <A HREF="special.html#class.copy">class.copy</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Bill Wade
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>11 Nov 1999<BR>



<P>12.8&nbsp;



 <A HREF="special.html#class.copy">class.copy</A>
 paragraph 15 refers only
to "temporary class objects."  It needs to be made clear that these
provisions do <B>not</B> apply to temporaries that have been bound to
references.  For instance,</P>

<PRE>
    struct A {
        mutable int value;
        explicit A(int i) : value(i) {}
        void mutate(int i) const { value = i; }
    };

    int foo() {
        A const&amp; t = A(1);
        A n(t);          // can this copy be elided?
        t.mutate(2);
        return n.value;  // can this return 2?
    }
</PRE>

The current wording seems to allow an implementation not to perform
the copy in <TT>A N(t)</TT> because the source object is a temporary
(created explicitly by <TT>A(1)</TT>).

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>Change the wording proposed in the resolution of <A HREF="
     cwg_defects.html#20">issue 20</A> from</P>

<BLOCKQUOTE>
<UL>
<LI>when a temporary class object (12.2&nbsp;



 <A HREF="special.html#class.temporary">class.temporary</A>)
would be copied to a class object...</LI>
</UL>
</BLOCKQUOTE>

<P>to</P>

<BLOCKQUOTE>
<UL>
<LI>when a temporary class object that has not been bound to a
reference (12.2&nbsp;



 <A HREF="special.html#class.temporary">class.temporary</A>) would be copied to a class
object...</LI>
</UL>
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="59"></A>
<H4>59.
  
Clarification of overloading and UDC to reference type
</H4>
<B>Section: </B>13.3.1.4&nbsp;



 <A HREF="over.html#over.match.copy">over.match.copy</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Adamczyk
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>13 Oct 1998<BR>



<P>Sections
13.3.1.4&nbsp;



 <A HREF="over.html#over.match.copy">over.match.copy</A>

 and
13.3.1.5&nbsp;



 <A HREF="over.html#over.match.conv">over.match.conv</A>


should be clarified regarding the treatment of conversion functions which
return reference types.</P>

<P>
<B>Proposed resolution (10/99):</B>
</P>

<P>In
13.3.1.4&nbsp;



 <A HREF="over.html#over.match.copy">over.match.copy</A>

 paragraph
1, change</P>
<BLOCKQUOTE>Conversion functions that return "reference to <TT>T</TT>"
return lvalues
of type <TT>T</TT> and are therefore considered to yield <TT>T</TT>
for this process of selecting
candidate functions.</BLOCKQUOTE>
to
<BLOCKQUOTE>Conversion functions that return "reference to <TT>X</TT>"
return lvalues
of type <TT>X</TT> and are therefore considered to yield <TT>X</TT>
for this process of selecting
candidate functions.</BLOCKQUOTE>
In
13.3.1.5&nbsp;



 <A HREF="over.html#over.match.conv">over.match.conv</A>

 paragraph 1,
change
<BLOCKQUOTE>Conversion functions that return "reference to <TT>T</TT>"
return lvalues
of type <TT>T</TT> and are therefore considered to yield <TT>T</TT>
for this process of selecting
candidate functions.</BLOCKQUOTE>
to
<BLOCKQUOTE>Conversion functions that return "reference to
<I>cv2</I> <TT>X</TT>"
return lvalues of type "<I>cv2</I> <TT>X</TT>" and are therefore
considered to yield
<TT>X</TT> for this process of selecting candidate functions.</BLOCKQUOTE>
<BR>
<BR>
<HR>
<A NAME="51"></A>
<H4>51.
  
Overloading and user-defined conversions
</H4>
<B>Section: </B>13.3.3&nbsp;



 <A HREF="over.html#over.match.best">over.match.best</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Adamczyk
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>13 Oct 1998<BR>



<P>In 13.3.3&nbsp;



 <A HREF="over.html#over.match.best">over.match.best</A>
 paragraph 1,
bullet 4 of the second set of bullets, there is a cross-reference
to 8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A>
 and
13.3.1.5&nbsp;



 <A HREF="over.html#over.match.conv">over.match.conv</A>
. I believe it should also
reference 13.3.1.6&nbsp;



 <A HREF="over.html#over.match.ref">over.match.ref</A>
.
I think the phrase "initialization by user-defined
conversion" was intended to refer to all initializations using user-defined
conversions, and not just the case in 
13.3.1.5&nbsp;



 <A HREF="over.html#over.match.conv">over.match.conv</A>
. Referring to only
13.3.1.5&nbsp;



 <A HREF="over.html#over.match.conv">over.match.conv</A>
 suggests a narrower
meaning of the phrase.</P>

<P>13.3.1.4&nbsp;



 <A HREF="over.html#over.match.copy">over.match.copy</A>
,
although it does deal with initialization by user-defined
conversion, does not need to be referenced because it deals with class
&mdash;&gt; class cases, and therefore there are no standard conversions involved
that could be compared.</P>

<BR>
<BR>
<HR>
<A NAME="84"></A>
<H4>84.
  
Overloading and conversion loophole used by <TT>auto_ptr</TT>
</H4>
<B>Section: </B>13.3.3.1&nbsp;



 <A HREF="over.html#over.best.ics">over.best.ics</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Adamczyk
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>10 Dec 1998<BR>



<P>By the letter of the standard, the conversions required to
make <TT>auto_ptr</TT> work should be accepted.</P>

<P>However, there's good reason to wonder if there isn't a bug in the standard
here. Here's the issue: line 16 in the example below comes down to
<BLOCKQUOTE>copy-initialize an <TT>auto_ptr&lt;Base&gt;</TT> from
an <TT>auto_ptr&lt;Derived&gt;</TT> rvalue</BLOCKQUOTE>
To do that, we first look to see whether we can convert
an <TT>auto_ptr&lt;Derived&gt;</TT>
to an <TT>auto_ptr&lt;Base&gt;</TT>, by enumerating the
constructors of <TT>auto_ptr&lt;Base&gt;</TT>
and the conversion functions of <TT>auto_ptr&lt;Derived&gt;</TT>.
There's a single possible way to do the conversion, namely the conversion
function</P>
<PRE>
    auto_ptr&lt;Derived&gt;::operator auto_ptr&lt;Base&gt;()
</PRE>
(generated from the template).  (The constructor 
<TT>auto_ptr&lt;Base&gt;(auto_ptr_ref&lt;Base&gt;)</TT>
doesn't work because it requires a  user-defined conversion on the
argument.)
    
<P>So far, so good.  Now, we do the copy step:</P>
<BLOCKQUOTE>direct-initialize an <TT>auto_ptr&lt;Base&gt;</TT>
from an <TT>auto_ptr&lt;Base&gt;</TT>
rvalue</BLOCKQUOTE>
This, as we've gone to great lengths to set up, is done by calling 
the conversion function
<PRE>
    auto_ptr&lt;Base&gt;::operator auto_ptr_ref&lt;Base&gt;()
</PRE>
(generated from the template), and then the constructor
<PRE>
    auto_ptr&lt;Base&gt;(auto_ptr_ref&lt;Base&gt;)
</PRE>
(generated from the template).
    
<P>The problem with this interpretation is that it violates the long-standing 
common-law rule that only a single user-defined conversion will be called 
to do an implicit conversion.  I find that pretty disturbing. 
(In fact, the full operation involves two conversion functions and two
constructors, but "copy" constructors are generally considered not to be
conversions.)</P>
    
<P>The direct-initialization second step of a copy-initialization was intended
to be a simple copy &mdash; you've made a temporary, and now you use a copy
constructor to copy it.  Because it is defined in terms of direct
initialization, however, it can exploit the loophole that auto_ptr
is based on.</P>
    
<P>To switch to personal opinion for a second, I think it's bad enough
that auto_ptr has to exploit a really arcane loophole of overload resolution,
but in this case it seems like it's exploiting a loophole on a loophole.</P>
<PRE>
    struct Base {                             //  2
       static void sink(auto_ptr&lt;Base&gt;);      //  3
    };                                        //  4

    struct Derived : Base {                   //  5
       static void sink(auto_ptr&lt;Derived&gt;);   //  6
    };                                        //  7

    auto_ptr&lt;Derived&gt; source() {              //  8
       auto_ptr&lt;Derived&gt; p(source());         //  9
       auto_ptr&lt;Derived&gt; pp(p);               // 10
       Derived::sink(source());               // 11
       p = pp;                                // 12
       p = source();                          // 13
       auto_ptr&lt;Base&gt; q(source());            // 14
       auto_ptr&lt;Base&gt; qp(p);                  // 15
       Base::sink(source());                  // 16
       q = pp;                                // 17
       q = source();                          // 18
       return p;                              // 19
       return source();
    }
</PRE>

<U>Derek Inglis</U>:



<P>It seems clear to me that the result of this direct initilization
must be the second standard conversion sequence in a user defined
conversion sequence.  Otherwise the resulting conversion sequence is
not an implicit conversion sequence.  By the letter of the standard,
the sequence of conversions making up a copy-initialization must be an
implicit conversion sequence.</P>

<P>Paragraph 3 of clause 4&nbsp;



 <A HREF="conv.html#conv">conv</A>:</P>

<BLOCKQUOTE>

An expression <TT>e</TT> can be <I>implicitly converted</I> to a type
<TT>T</TT> if and only if the declaration "<TT>T t=e;</TT>" is
well-formed, for some invented temporary variable <TT>t</TT>
(8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A>).

</BLOCKQUOTE>

<P>Paragraph 1 of 13.3.3.1&nbsp;



 <A HREF="over.html#over.best.ics">over.best.ics</A>:</P>

<BLOCKQUOTE>

An <I>implicit conversion sequence</I> is a sequence of conversions
used to convert an argument in a function call to the type of the
corresponding parameter of the function being called.  The sequence of
conversions is an implicit conversion as defined in clause
4&nbsp;



 <A HREF="conv.html#conv">conv</A>, which means it is governed by the rules for
initialization of an object or reference by a single expression
(8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A>, 8.5.3&nbsp;



 <A HREF="decl.html#dcl.init.ref">dcl.init.ref</A>).

</BLOCKQUOTE>

Sentence 1 of paragraph 12 of 8.5&nbsp;



 <A HREF="decl.html#dcl.init">dcl.init</A>:

<BLOCKQUOTE>

The initialization that occurs in argument passing ...
is  called <I>copy-initialization</I> and is equivalent to  the form

<PRE>
     T x = a;
</PRE>

</BLOCKQUOTE>

<P>For me, these sentences imply that all sequences of conversions
permitted on a function argument must be valid implicit conversion
sequences.</P>

<P>The 'loophole' can be closed by adding a sentence (or note) to the
section describing the 'direct initialization second step of a copy
initialization' stating that the copy initialization is ill-formed if
the conversion sequence resulting from the direct initialization is
not a standard conversion sequence.</P>

<P>(See also <A HREF="
     cwg_defects.html#177">issue 177</A> and paper
J16/00-0009 = WG21 N1232.)</P>

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>Change 13.3.3.1&nbsp;



 <A HREF="over.html#over.best.ics">over.best.ics</A> paragraphs 3 and 4 from</P>

<BLOCKQUOTE>

<P>Except in the context of an initialization by user-defined
conversion (13.3.1.4&nbsp;



 <A HREF="over.html#over.match.copy">over.match.copy</A>,
13.3.1.5&nbsp;



 <A HREF="over.html#over.match.conv">over.match.conv</A>), a well-formed implicit conversion
sequence is one of the following forms:</P>

<UL>

<LI>a <I>standard conversion sequence</I>
(13.3.3.1.1&nbsp;



 <A HREF="over.html#over.ics.scs">over.ics.scs</A>),</LI>

<LI>a <I>user-defined conversion sequence</I>
(13.3.3.1.2&nbsp;



 <A HREF="over.html#over.ics.user">over.ics.user</A>), or</LI>

<LI>an <I>ellipsis conversion sequence
(13.3.3.1.3&nbsp;



 <A HREF="over.html#over.ics.ellipsis">over.ics.ellipsis</A>)</I>
</LI>

</UL>

<P>In the context of an initialization by user-defined conversion (i.e.,
when considering the argument of a user-defined conversion function;
see 13.3.1.4&nbsp;



 <A HREF="over.html#over.match.copy">over.match.copy</A>, 13.3.1.5&nbsp;



 <A HREF="over.html#over.match.conv">over.match.conv</A>),
only standard conversion sequences and
ellipsis conversion sequences are allowed.</P>

</BLOCKQUOTE>

<P>to</P>

<BLOCKQUOTE>

<P>A well-formed implicit conversion
sequence is one of the following forms:</P>

<UL>

<LI>a <I>standard conversion sequence</I>
(13.3.3.1.1&nbsp;



 <A HREF="over.html#over.ics.scs">over.ics.scs</A>),</LI>

<LI>a <I>user-defined conversion sequence</I>
(13.3.3.1.2&nbsp;



 <A HREF="over.html#over.ics.user">over.ics.user</A>), or</LI>

<LI>an <I>ellipsis conversion sequence</I>
(13.3.3.1.3&nbsp;



 <A HREF="over.html#over.ics.ellipsis">over.ics.ellipsis</A>)</LI>

</UL>

<P>However, when considering the argument of a user-defined conversion
function that is a candidate by 13.3.1.3&nbsp;



 <A HREF="over.html#over.match.ctor">over.match.ctor</A>
when invoked for the copying
of the temporary in the second step of a class copy-initialization, or
by 13.3.1.4&nbsp;



 <A HREF="over.html#over.match.copy">over.match.copy</A>, 13.3.1.5&nbsp;



 <A HREF="over.html#over.match.conv">over.match.conv</A>,
or 13.3.1.6&nbsp;



 <A HREF="over.html#over.match.ref">over.match.ref</A> in all cases, only standard
conversion sequences and ellipsis conversion sequences are
allowed.</P>

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="83"></A>
<H4>83.
  
Overloading and deprecated conversion of string literal
</H4>
<B>Section: </B>13.3.3.2&nbsp;



 <A HREF="over.html#over.ics.rank">over.ics.rank</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Adamczyk
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>24 Jan 1999<BR>



<P>In
13.3.3.2&nbsp;



 <A HREF="over.html#over.ics.rank">over.ics.rank</A>
, we have</P>
<UL>
<LI>
<TT>S1</TT> and <TT>S2</TT> differ only in their
qualification conversion and
yield similar types <TT>T1</TT> and <TT>T2</TT>
(4.4&nbsp;



 <A HREF="conv.html#conv.qual">conv.qual</A>
),
respectively, and the cv-qualification signature of type <TT>T1</TT>
is a proper
subset of the cv-qualification signature of type <TT>T2</TT>,
[<I>Example:</I>
<PRE>
    int f(const int *);
    int f(int *); 
    int i;
    int j = f(&amp;i); // <I>Calls</I> f(int *)
</PRE>
&mdash;<I>end example</I>] or, if not that,</LI>
</UL>
This does not work right with respect to the deprecated conversion from
string literal to "<TT>char *</TT>". Consider
<PRE>
    void f(char *);
    void f(const char *);
    
    f("abc");
</PRE>
The two conversion sequences differ only in their qualification conversions,
and the destination types are similar. The cv-qualification signature of
"<TT>char *</TT>", is a proper subset of the cv-qualification signature
of "<TT>const char *</TT>", so <TT>f(char *)</TT> is chosen, which is wrong.
The rule should be like the one for conversion to bool &mdash; the deprecated
conversion should be worse than another exact match that is not the deprecated
conversion.

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>Change
13.3.3.2&nbsp;



 <A HREF="over.html#over.ics.rank">over.ics.rank</A>
 paragraph 3 bullet 1
sub-bullet 3 from</P>
<BLOCKQUOTE>
<TT>S1</TT> and <TT>S2</TT> differ only in their qualification
conversion and yield similar types <TT>T1</TT> and <TT>T2</TT>
(4.4&nbsp;



 <A HREF="conv.html#conv.qual">conv.qual</A>
), respectively, and the
cv-qualification signature of type <TT>T1</TT> is a proper subset of
the cv-qualification signature of type <TT>T2</TT>.
</BLOCKQUOTE>
to
<BLOCKQUOTE>
<TT>S1</TT> and <TT>S2</TT> differ only in their qualification
conversion and yield similar types <TT>T1</TT> and <TT>T2</TT>
(4.4&nbsp;



 <A HREF="conv.html#conv.qual">conv.qual</A>
), respectively, and the
cv-qualification signature of type <TT>T1</TT> is a proper subset of
the cv-qualification signature of type <TT>T2</TT>, and <TT>S1</TT> is
not the deprecated string literal array-to-pointer conversion
(4.2&nbsp;



 <A HREF="conv.html#conv.array">conv.array</A>
).
</BLOCKQUOTE>
<BR>
<BR>
<HR>
<A NAME="153"></A>
<H4>153.
  
Misleading wording (rank of conversion)
</H4>
<B>Section: </B>13.3.3.2&nbsp;



 <A HREF="over.html#over.ics.rank">over.ics.rank</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Valentin Bonnard
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>6 Aug 1999<BR>



<P>13.3.3.2&nbsp;



 <A HREF="over.html#over.ics.rank">over.ics.rank</A>
 paragraph 3 bullet 1
sub-bullet 2 says,</P>

<BLOCKQUOTE>
the rank of <TT>S1</TT> is better than the rank of <TT>S2</TT> (by the
rules defined below)...
</BLOCKQUOTE>

This wording is confusing.  The word "below" refers to paragraph 4
(which may not be clear), and the bulk of paragraph 4 deals with
comparing conversion sequences whose "rank" is the same.

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>In
13.3.3.2&nbsp;



 <A HREF="over.html#over.ics.rank">over.ics.rank</A>
 paragraph 3, change</P>
<BLOCKQUOTE>
the rank of <TT>S1</TT> is better than the rank of <TT>S2</TT> (by the
rules defined below)
</BLOCKQUOTE>
to
<BLOCKQUOTE>
the rank of <TT>S1</TT> is better than the rank of <TT>S2</TT>, or
<TT>S1</TT> and <TT>S2</TT> have the same rank and are distinguishable
by the rules in the paragraph below
</BLOCKQUOTE>
<BR>
<BR>
<HR>
<A NAME="202"></A>
<H4>202.
  
Use of overloaded function name
</H4>
<B>Section: </B>13.4&nbsp;



 <A HREF="over.html#over.over">over.over</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Clamage
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>2 Feb 2000<BR>





<P>13.4&nbsp;



 <A HREF="over.html#over.over">over.over</A>
 paragraph 1 contains a
supposedly exhaustive list of contexts in which the name of an
overloaded function can be used without an argument list ("...shall
not be used without arguments in contexts other than those listed").
However, 14.3.2&nbsp;



 <A HREF="template.html#temp.arg.nontype">temp.arg.nontype</A>
 paragraph 5,
bullet 4 gives another context: as a template nontype argument.</P>

<P>
<B>Suggested resolution:</B> Add the missing case to
13.4&nbsp;



 <A HREF="over.html#over.over">over.over</A>.</P>

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>Add as the final bullet in 13.4&nbsp;



 <A HREF="over.html#over.over">over.over</A> paragraph 1:</P>

<BLOCKQUOTE>
<UL>
<LI>a non-type template-parameter (14.3.2&nbsp;



 <A HREF="template.html#temp.arg.nontype">temp.arg.nontype</A>).</LI>
</UL>
</BLOCKQUOTE>

<P>and adjust the "or" and final period on the preceding
two bullets.</P>

<BR>
<BR>
<HR>
<A NAME="250"></A>
<H4>250.
  
Address of function template specialization with non-deduced template arguments
</H4>
<B>Section: </B>13.4&nbsp;



 <A HREF="over.html#over.over">over.over</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Nikolas Kauer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>10 Oct 2000<BR>


<P>13.4&nbsp;



 <A HREF="over.html#over.over">over.over</A> paragraph 2 says,</P>

<BLOCKQUOTE>

If the name is a function template, template argument deduction is
done (14.8.2.2&nbsp;



 <A HREF="template.html#temp.deduct.funcaddr">temp.deduct.funcaddr</A>), and if the argument
deduction succeeds, the deduced template arguments are used to
generate a single template function, which is added to the set of
overloaded functions considered.

</BLOCKQUOTE>

<P>It is not clear whether this formulation allows explicit
specification of non-deduced template arguments.  For instance,</P>

<PRE>
    template &lt;int I&gt; void f(double x[]);
    typedef void (*FPtr)(double x[]);
    FPtr fp = &amp;f&lt;3&gt;;
</PRE>

<P>If only deduced arguments can be used, this example is
ill-formed.</P>

<P>
<B>Suggested resolution:</B> Clarify 13.4&nbsp;



 <A HREF="over.html#over.over">over.over</A>
paragraph 2 to allow both deduced and explicitly-specified
template arguments to be used to determine the function template
specialization to be added to the overload set.</P>

<P>(See also issues <A HREF="
     cwg_defects.html#115">115</A> and
<A HREF="
     cwg_defects.html#214">214</A>.)</P>

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>In 13.4&nbsp;



 <A HREF="over.html#over.over">over.over</A> paragraph 2, change</P>

<BLOCKQUOTE>

...if the argument deduction succeeds, the deduced template arguments
are used to generate a single template function...

</BLOCKQUOTE>

<P>to</P>

<BLOCKQUOTE>

...if the argument deduction succeeds, the resulting template
argument list is used to generate a single function template
specialization...

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="32"></A>
<H4>32.
  
Clarification of explicit instantiation of non-exported templates
</H4>
<B>Section: </B>14&nbsp;



 <A HREF="template.html#temp">temp</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Daveed Vandevoorde
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>10 Jul 1998<BR>





<P>Section 14&nbsp;



 <A HREF="template.html#temp">temp</A>
 paragraph 8 says:
<BLOCKQUOTE>A non-exported template that is neither explicitly specialized
<U>nor explicitly instantiated</U> must be defined in every translation
unit in which it is implicitly instantiated (14.7.1&nbsp;



 <A HREF="template.html#temp.inst">temp.inst</A>
) or <U>explicitly
instantiated</U> (14.7.2&nbsp;



 <A HREF="template.html#temp.explicit">temp.explicit</A>
); no diagnostic is required.</BLOCKQUOTE>
Shouldn't the first underlined phrase be omitted to avoid conflict with
the second underlined phrase?</P>

<P>
<U>From John Spicer:</U>
</P>

<P>The first "explicitly instantiated" is intended to mean "explicitly instantiated
in some other translation unit".</P>

<P>
<B>Proposed Resolution (04/99):</B>
Change the text in 14&nbsp;



 <A HREF="template.html#temp">temp</A>
 paragraph 8 from:</P>
<BLOCKQUOTE>A non-exported template that is neither explicitly specialized
nor explicitly instantiated must be defined in every translation unit in
which it is implicitly instantiated (14.7.1&nbsp;



 <A HREF="template.html#temp.inst">temp.inst</A>
) or explicitly instantiated
(14.7.2&nbsp;



 <A HREF="template.html#temp.explicit">temp.explicit</A>
); no diagnostic is required.</BLOCKQUOTE>
to:
<BLOCKQUOTE>A non-exported template must be defined in every translation
unit in which it is implicitly instantiated (14.7.1&nbsp;



 <A HREF="template.html#temp.inst">temp.inst</A>
), unless the corresponding
specialization is explicitly instantiated (14.7.2&nbsp;



 <A HREF="template.html#temp.explicit">temp.explicit</A>
) in some translation
unit; no diagnostic is required. [<I>Note:</I> See also 14.7.2&nbsp;



 <A HREF="template.html#temp.explicit">temp.explicit</A>
]</BLOCKQUOTE>
<BR>
<BR>
<HR>
<A NAME="105"></A>
<H4>105.
  
Meaning of "template function"
</H4>
<B>Section: </B>14&nbsp;



 <A HREF="template.html#temp">temp</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Daveed Vandevoorde
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>16 Apr 1999<BR>



<P>The phrase "template function" is sometimes used to refer to a
template (e.g., in 14&nbsp;



 <A HREF="template.html#temp">temp</A>
 paragraph 8)
and sometimes to refer to a function generated from a template (e.g.,
13.4&nbsp;



 <A HREF="over.html#over.over">over.over</A>
 paragraph 4).</P>

<P>
<B>Suggested Resolution:</B>
</P>

<P>The phrase should mean "a function generated from a template"
(or might perhaps include explicit specializations).</P>

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>In 1.3.10&nbsp;



 <A HREF="intro.html#defns.signature">defns.signature</A> paragraph 10, replace "template function specialization"
by "function template specialization".
</P>

<P>In 9.3&nbsp;



 <A HREF="class.html#class.mfct">class.mfct</A> paragraph 2, replace "template
member functions" by "member functions of class templates and
member function templates."</P>

<P>In 13.3.1&nbsp;



 <A HREF="over.html#over.match.funcs">over.match.funcs</A> paragraph 7 and footnote, replace
all instances of "template functions" by "function template
specializations."</P>

<P>In 13.3.3&nbsp;



 <A HREF="over.html#over.match.best">over.match.best</A> paragraph 1, fourth bullet (counting all
bullets in that paragraph), replace "template function specialization" by
"function template specialization".  In the fifth bullet, replace
"template functions" by "function template specializations."
</P>

<P>In 13.4&nbsp;



 <A HREF="over.html#over.over">over.over</A> paragraph 2, replace "template
function" by "function template specialization."</P>

<P>Change 13.4&nbsp;



 <A HREF="over.html#over.over">over.over</A> paragraph 4 from:
<BLOCKQUOTE>If more than one function is selected, any template functions
in the set are eliminated if the set also contains a non-template function,
and any given template function is eliminated if the set contains a second
template function that is more specialized than the first according to
the partial ordering rules of 14.5.5.2&nbsp;



 <A HREF="template.html#temp.func.order">temp.func.order</A>. After such eliminations, if any,
there shall remain exactly one selected function.</BLOCKQUOTE>
to:
<BLOCKQUOTE>If more than one function is selected, any function
template specializations
in the set are eliminated if the set also contains a non-template function,
and any given function template specialization <TT>F1</TT> is eliminated if the set contains a
second function template specialization whose function template is more specialized than
the function template of <TT>F1</TT> according to the partial ordering rules of
14.5.5.2&nbsp;



 <A HREF="template.html#temp.func.order">temp.func.order</A>. After such eliminations, if any, there shall remain exactly one
selected function.</BLOCKQUOTE>
</P>
<P>Change text in section 14&nbsp;



 <A HREF="template.html#temp">temp</A> paragraph 8 from:
<BLOCKQUOTE>A template function declared both exported and inline is just
inline and not exported.</BLOCKQUOTE>
to:
<BLOCKQUOTE>A function template declared both exported and inline is just
inline and not exported.</BLOCKQUOTE>
</P>

<P>In 14.5.3&nbsp;



 <A HREF="template.html#temp.friend">temp.friend</A> paragraph 1, third bullet, replace
"template function" by "function template" and "function
specialization" by "function template specialization."</P>

<P>In footnote 130 (14.5.5&nbsp;



 <A HREF="template.html#temp.fct">temp.fct</A> paragraph 2),
replace "template functions" by "function template specializations."</P>

<P>In 14.5.5.2&nbsp;



 <A HREF="template.html#temp.func.order">temp.func.order</A> paragraph 1, third bullet change "template
function specialization" to "function template specialization".
</P>
<P>In 14.8.2&nbsp;



 <A HREF="template.html#temp.deduct">temp.deduct</A> paragraph 1, change "template function specialization"
to "function template specialization".
</P>
<P>In 17.1.5&nbsp;



 <A HREF="lib-intro.html#defns.component">defns.component</A> change "non-member template functions that
operate" to "non-member function templates that operate".
</P>
<P>In 17.1.18&nbsp;



 <A HREF="lib-intro.html#defns.traits">defns.traits</A> change "template classes and template functions"
to "class templates and function templates".
</P>
<P>In 20.2&nbsp;



 <A HREF="lib-utilities.html#lib.utility">lib.utility</A> paragraph 1 change:
<BLOCKQUOTE>This subclause contains some basic template functions and classes
that are used throughout the rest of the library.</BLOCKQUOTE>
to:
<BLOCKQUOTE>This subclause contains some basic function and class templates
that are used throughout the rest of the library.</BLOCKQUOTE>
</P>
<P>In 20.2.2&nbsp;



 <A HREF="lib-utilities.html#lib.pairs">lib.pairs</A> paragrah 1 change "template function" to "function
template".
</P>
<P>In footnote 215 (20.3.7&nbsp;



 <A HREF="lib-utilities.html#lib.function.pointer.adaptors">lib.function.pointer.adaptors</A> paragraph 6)
change "template functions" to "function templates".
</P>
<P>In 22.1.1&nbsp;



 <A HREF="lib-locales.html#lib.locale">lib.locale</A> paragraph 4 change "template function" to "function
template".
</P>
<P>In 24.1&nbsp;



 <A HREF="lib-iterators.html#lib.iterator.requirements">lib.iterator.requirements</A> paragraph 2 change "template function"
to "function template".
</P>

<P>In 24.3.3&nbsp;



 <A HREF="lib-iterators.html#lib.std.iterator.tags">lib.std.iterator.tags</A> paragraph 1, change "template
function" to "function template specialization."</P>

<P>In 24.3.4&nbsp;



 <A HREF="lib-iterators.html#lib.iterator.operations">lib.iterator.operations</A> paragraph 1 change "template function"
to "function template", and "These functions use" to "These function templates
use".
</P>
<P>In the section heading of 27.6.2.5.4&nbsp;



 <A HREF="lib-iostreams.html#lib.ostream.inserters.character">lib.ostream.inserters.character</A>
change "template functions" to "function templates".
</P>
<P>In 17.3.1.2&nbsp;



 <A HREF="lib-intro.html#lib.structure.requirements">lib.structure.requirements</A> paragraph 2 change "template
class name <TT>char_traits</TT>" to "class template <TT>char_traits</TT>".
</P>
<P>In the section heading of 18.2.1.1&nbsp;



 <A HREF="lib-support.html#lib.numeric.limits">lib.numeric.limits</A> change "Template
class" to "Class template".
</P>
<P>In 20.1.5&nbsp;



 <A HREF="lib-utilities.html#lib.allocator.requirements">lib.allocator.requirements</A> paragraph 3 change "template
class member <TT>rebind</TT>" to "member class template <TT>rebind</TT>"
and change "template typedef" to "typedef template".
</P>
<P>In the section heading of 20.3.6.1&nbsp;



 <A HREF="lib-utilities.html#lib.binder.1st">lib.binder.1st</A> change "Template
class" to "Class template".
</P>
<P>In the section heading of 20.3.6.3&nbsp;



 <A HREF="lib-utilities.html#lib.binder.2nd">lib.binder.2nd</A> change "Template
class" to "Class template".
</P>
<P>In the section heading of 20.4.5&nbsp;



 <A HREF="lib-utilities.html#lib.auto.ptr">lib.auto.ptr</A> change "Template class"
to "Class template".
</P>
<P>In the section heading of 21.3&nbsp;



 <A HREF="lib-strings.html#lib.basic.string">lib.basic.string</A> change "Template
class" to "Class template".
</P>
<P>In 21.3&nbsp;



 <A HREF="lib-strings.html#lib.basic.string">lib.basic.string</A> paragraphs 1 and 2 change "template class
<TT>basic_string</TT>"
to "class template <TT>basic_string</TT>".
</P>
<P>In the section heading of 22.2.1.1&nbsp;



 <A HREF="lib-locales.html#lib.locale.ctype">lib.locale.ctype</A> change "Template
class" to "Class template".
</P>
<P>In the section heading of 22.2.1.2&nbsp;



 <A HREF="lib-locales.html#lib.locale.ctype.byname">lib.locale.ctype.byname</A> change
"Template class" to "Class template".
</P>
<P>In the section heading of 22.2.1.5&nbsp;



 <A HREF="lib-locales.html#lib.locale.codecvt">lib.locale.codecvt</A> change "Template
class" to "Class template".
</P>
<P>In the section heading of 22.2.1.6&nbsp;



 <A HREF="lib-locales.html#lib.locale.codecvt.byname">lib.locale.codecvt.byname</A> change
"Template class" to "Class template".
</P>
<P>In the section heading of 22.2.2.1&nbsp;



 <A HREF="lib-locales.html#lib.locale.num.get">lib.locale.num.get</A> change "Template
class" to "Class template".
</P>
<P>In the section heading of 22.2.2.2&nbsp;



 <A HREF="lib-locales.html#lib.locale.nm.put">lib.locale.nm.put</A> change "Template
class" to "Class template".
</P>
<P>In the section heading of 22.2.3.1&nbsp;



 <A HREF="lib-locales.html#lib.locale.numpunct">lib.locale.numpunct</A> change "Template
class" to "Class template".
</P>
<P>In the section heading of 22.2.3.2&nbsp;



 <A HREF="lib-locales.html#lib.locale.numpunct.byname">lib.locale.numpunct.byname</A> change
"Template class" to "Class template".
</P>
<P>In the section heading of 22.2.4.1&nbsp;



 <A HREF="lib-locales.html#lib.locale.collate">lib.locale.collate</A> change "Template
class" to "Class template".
</P>
<P>In the section heading of 22.2.4.2&nbsp;



 <A HREF="lib-locales.html#lib.locale.collate.byname">lib.locale.collate.byname</A> change
"Template class" to "Class template".
</P>
<P>In the section heading of 22.2.5.1&nbsp;



 <A HREF="lib-locales.html#lib.locale.time.get">lib.locale.time.get</A> change "Template
class" to "Class template".
</P>
<P>In the section heading of 22.2.5.2&nbsp;



 <A HREF="lib-locales.html#lib.locale.time.get.byname">lib.locale.time.get.byname</A> change
"Template class" to "Class template".
</P>
<P>In the section heading of 22.2.5.3&nbsp;



 <A HREF="lib-locales.html#lib.locale.time.put">lib.locale.time.put</A> change "Template
class" to "Class template".
</P>
<P>In the section heading of 22.2.5.4&nbsp;



 <A HREF="lib-locales.html#lib.locale.time.put.byname">lib.locale.time.put.byname</A> change
"Template class" to "Class template".
</P>
<P>In the section heading of 22.2.6.1&nbsp;



 <A HREF="lib-locales.html#lib.locale.money.get">lib.locale.money.get</A> change "Template
class" to "Class template".
</P>
<P>In the section heading of 22.2.6.2&nbsp;



 <A HREF="lib-locales.html#lib.locale.money.put">lib.locale.money.put</A> change "Template
class" to "Class template".
</P>
<P>In the section heading of 22.2.6.3&nbsp;



 <A HREF="lib-locales.html#lib.locale.moneypunct">lib.locale.moneypunct</A> change "Template
class" to "Class template".
</P>
<P>In the section heading of 22.2.6.4&nbsp;



 <A HREF="lib-locales.html#lib.locale.moneypunct.byname">lib.locale.moneypunct.byname</A> change
"Template class" to "Class template".
</P>
<P>In the section heading of 22.2.7.1&nbsp;



 <A HREF="lib-locales.html#lib.locale.messages">lib.locale.messages</A> change "Template
class" to "Class template".
</P>
<P>In the section heading of 22.2.7.2&nbsp;



 <A HREF="lib-locales.html#lib.locale.messages.byname">lib.locale.messages.byname</A> change
"Template class" to "Class template".
</P>
<P>In the section heading of 23.2.1&nbsp;



 <A HREF="lib-containers.html#lib.deque">lib.deque</A> change "Template class"
to "Class template".
</P>
<P>In the section heading of 23.2.2&nbsp;



 <A HREF="lib-containers.html#lib.list">lib.list</A> change "Template class"
to "Class template".
</P>
<P>In the section heading of 23.2.3.1&nbsp;



 <A HREF="lib-containers.html#lib.queue">lib.queue</A> change "Template class"
to "Class template".
</P>
<P>In the section heading of 23.2.3.2&nbsp;



 <A HREF="lib-containers.html#lib.priority.queue">lib.priority.queue</A> change "Template
class" to "Class template".
</P>
<P>In the section heading of 23.2.3.3&nbsp;



 <A HREF="lib-containers.html#lib.stack">lib.stack</A> change "Template class"
to "Class template".
</P>
<P>In the section heading of 23.2.4&nbsp;



 <A HREF="lib-containers.html#lib.vector">lib.vector</A> change "Template class"
to "Class template".
</P>
<P>In the section heading of 23.3.1&nbsp;



 <A HREF="lib-containers.html#lib.map">lib.map</A> change "Template class"
to "Class template".
</P>
<P>In the section heading of 23.3.2&nbsp;



 <A HREF="lib-containers.html#lib.multimap">lib.multimap</A> change "Template class"
to "Class template".
</P>
<P>In the section heading of 23.3.3&nbsp;



 <A HREF="lib-containers.html#lib.set">lib.set</A> change "Template class"
to "Class template".
</P>
<P>In the section heading of 23.3.4&nbsp;



 <A HREF="lib-containers.html#lib.multiset">lib.multiset</A> change "Template class"
to "Class template".
</P>
<P>In the section heading of 23.3.5&nbsp;



 <A HREF="lib-containers.html#lib.template.bitset">lib.template.bitset</A> change "Template
class" to "Class template".
</P>
<P>In 23.3.5&nbsp;



 <A HREF="lib-containers.html#lib.template.bitset">lib.template.bitset</A> paragraph 1, change "template class"
to "class template".
</P>
<P>In the section heading of 24.4.1.1&nbsp;



 <A HREF="lib-iterators.html#lib.reverse.iterator">lib.reverse.iterator</A> change "Template
class" to "Class template".
</P>
<P>In the section heading of 24.4.2.1&nbsp;



 <A HREF="lib-iterators.html#lib.back.insert.iterator">lib.back.insert.iterator</A> change
"Template class" to "Class template".
</P>
<P>In the section heading of 24.4.2.3&nbsp;



 <A HREF="lib-iterators.html#lib.front.insert.iterator">lib.front.insert.iterator</A> change
"Template class" to "Class template".
</P>
<P>In the section heading of 24.4.2.5&nbsp;



 <A HREF="lib-iterators.html#lib.insert.iterator">lib.insert.iterator</A> change "Template
class" to "Class template".
</P>
<P>In 24.5&nbsp;



 <A HREF="lib-iterators.html#lib.stream.iterators">lib.stream.iterators</A> paragraph 1, change "template classes"
to "class templates".
</P>
<P>In the section heading of 24.5.1&nbsp;



 <A HREF="lib-iterators.html#lib.istream.iterator">lib.istream.iterator</A> change "Template
class" to "Class template".
</P>
<P>In the section heading of 24.5.2&nbsp;



 <A HREF="lib-iterators.html#lib.ostream.iterator">lib.ostream.iterator</A> [lib.ostream.iterator] change "Template
class" to "Class template".
</P>
<P>In the section heading of 24.5.3&nbsp;



 <A HREF="lib-iterators.html#lib.istreambuf.iterator">lib.istreambuf.iterator</A> change "Template
class" to "Class template".
</P>
<P>In 24.5.3&nbsp;



 <A HREF="lib-iterators.html#lib.istreambuf.iterator">lib.istreambuf.iterator</A> paragraph 1, change "template class"
to "class template".
</P>
<P>In the section heading of 24.5.3.1&nbsp;



 <A HREF="lib-iterators.html#lib.istreambuf.iterator::proxy">lib.istreambuf.iterator::proxy</A>
change "Template class" to "Class template".
</P>
<P>In the section heading of 24.5.4&nbsp;



 <A HREF="lib-iterators.html#lib.ostreambuf.iterator">lib.ostreambuf.iterator</A> change "Template
class" to "Class template".
</P>
<P>In 24.5.4&nbsp;



 <A HREF="lib-iterators.html#lib.ostreambuf.iterator">lib.ostreambuf.iterator</A> paragraph 1, change "template class"
to "class template".
</P>
<P>In 26.2&nbsp;



 <A HREF="lib-numerics.html#lib.complex.numbers">lib.complex.numbers</A> paragraph 1, change "template class"
to "class template".
</P>
<P>In the section heading of 26.2.2&nbsp;



 <A HREF="lib-numerics.html#lib.complex">lib.complex</A> change "Template class"
to "Class template".
</P>
<P>In 26.3.1&nbsp;



 <A HREF="lib-numerics.html#lib.valarray.synopsis">lib.valarray.synopsis</A> paragraph 1, change "template classes"
to "class templates" and change "function signatures" to "function templates".
</P>
<P>In the section heading of 26.3.2&nbsp;



 <A HREF="lib-numerics.html#lib.template.valarray">lib.template.valarray</A> change "Template
class" to "Class template".
</P>
<P>In the section heading of 26.3.5&nbsp;



 <A HREF="lib-numerics.html#lib.template.slice.array">lib.template.slice.array</A> change
"Template class" to "Class template".
</P>
<P>In the section heading of 26.3.7&nbsp;



 <A HREF="lib-numerics.html#lib.template.gslice.array">lib.template.gslice.array</A> change
"Template class" to "Class template".
</P>
<P>In the section heading of 26.3.8&nbsp;



 <A HREF="lib-numerics.html#lib.template.mask.array">lib.template.mask.array</A> change "Template
class" to "Class template".
</P>
<P>In the section heading of 26.3.9&nbsp;



 <A HREF="lib-numerics.html#lib.template.indirect.array">lib.template.indirect.array</A> change
"Template class" to "Class template".
</P>
<P>In 27.2&nbsp;



 <A HREF="lib-iostreams.html#lib.iostream.forward">lib.iostream.forward</A> [lib.iostream.forward] paragraphs 3 to 7, change "template
classes" to "class templates".
<I>[Note: Some editorial changes were made in paragraphs 2 to 8 when these
changes were applied in September 2001.]</I>
</P>
<P>In the section heading of 27.4.3&nbsp;



 <A HREF="lib-iostreams.html#lib.fpos">lib.fpos</A> change "Template class"
to "Class template".
</P>
<P>In the section heading of 27.4.4&nbsp;



 <A HREF="lib-iostreams.html#lib.ios">lib.ios</A> change "Template class"
to "Class template".
</P>
<P>In the section heading of 27.5.2&nbsp;



 <A HREF="lib-iostreams.html#lib.streambuf">lib.streambuf</A> change "Template class"
to "Class template".
</P>
<P>In 27.5.2&nbsp;



 <A HREF="lib-iostreams.html#lib.streambuf">lib.streambuf</A> paragraphs 2 and 3, change "template class"
to "class template".
</P>
<P>In the section heading of 27.6.1.1&nbsp;



 <A HREF="lib-iostreams.html#lib.istream">lib.istream</A> change "Template class"
to "Class template".
</P>
<P>In the section heading of 27.6.1.5&nbsp;



 <A HREF="lib-iostreams.html#lib.iostreamclass">lib.iostreamclass</A> change "Template
class" to "Class template".
</P>
<P>In the section heading of 27.6.2.1&nbsp;



 <A HREF="lib-iostreams.html#lib.ostream">lib.ostream</A> change "Template class"
to "Class template".
</P>
<P>In 27.7&nbsp;



 <A HREF="lib-iostreams.html#lib.string.streams">lib.string.streams</A> paragraph 1 change "template classes"
to "class templates".
</P>
<P>In the section heading of 27.7.1&nbsp;



 <A HREF="lib-iostreams.html#lib.stringbuf">lib.stringbuf</A> change "Template class"
to "Class template".
</P>
<P>In the section heading of 27.7.2&nbsp;



 <A HREF="lib-iostreams.html#lib.istringstream">lib.istringstream</A> change "Template
class" to "Class template".
</P>
<P>In the section heading of 27.7.4&nbsp;



 <A HREF="lib-iostreams.html#lib.stringstream">lib.stringstream</A> change "Template
class" to "Class template".
</P>
<P>In the section heading of 27.8.1.1&nbsp;



 <A HREF="lib-iostreams.html#lib.filebuf">lib.filebuf</A> change "Template class"
to "Class template".
</P>
<P>In the section heading of 27.8.1.5&nbsp;



 <A HREF="lib-iostreams.html#lib.ifstream">lib.ifstream</A> change "Template
class" to "Class template".
</P>
<P>In the section heading of 27.8.1.8&nbsp;



 <A HREF="lib-iostreams.html#lib.ofstream">lib.ofstream</A> change "Template
class" to "Class template".
</P>
<P>In the section heading of 27.8.1.11&nbsp;



 <A HREF="lib-iostreams.html#lib.fstream">lib.fstream</A> change "Template
class" to "Class template".</P>

<BR>
<BR>
<HR>
<A NAME="134"></A>
<H4>134.
  
Template classes and <I>declarator-id</I>s
</H4>
<B>Section: </B>14&nbsp;



 <A HREF="template.html#temp">temp</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>17 June 1999<BR>





<P>14&nbsp;



 <A HREF="template.html#temp">temp</A>
 paragraph 2 says,</P>

<BLOCKQUOTE>
[<I>Note:</I> in a class template declaration, if the
<I>declarator-id</I> is a <I>template-id</I>, the declaration
declares a class template partial specialization
(14.5.4&nbsp;



 <A HREF="template.html#temp.class.spec">temp.class.spec</A>
). ]
</BLOCKQUOTE>

There is no <I>declarator-id</I> in a class template declaration
(cf paragraph 3).

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>Replace the phrase "if the
<I>declarator-id</I> is a <I>template-id</I>" with "if the class name
is a <I>template-id</I>."</P>
<BR>
<BR>
<HR>
<A NAME="21"></A>
<H4>21.
  
Can a default argument for a template parameter appear in a friend declaration?
</H4>
<B>Section: </B>14.1&nbsp;



 <A HREF="template.html#temp.param">temp.param</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>unknown
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>unknown<BR>





<P>14.1&nbsp;



 <A HREF="template.html#temp.param">temp.param</A>
 paragraph 10 says:</P>
<BLOCKQUOTE>The set of default template-arguments available for use with
a template declaration or definition is obtained by merging the default
arguments from the definition (if in scope) and all declarations in scope
in the same way as default function arguments are (8.3.6&nbsp;



 <A HREF="decl.html#dcl.fct.default">dcl.fct.default</A>
)."</BLOCKQUOTE>
Can a default argument for a template argument appear in a friend declaration?
If so, when is this default argument considered for template instantiations?

<P>For example,</P>
<PRE>
    template&lt;class T1, class T2 = int&gt; class A;
 
    class B {
        template&lt;class T1 = int, class T2&gt; friend class A;
    };
</PRE>
Is this well-formed? If it is, should the IS say when the default argument
for <TT>T1</TT> is considered for instantiations of class <TT>A</TT>?

<P>
<B>Proposed resolution (10/00):</B> Add to the end of
14.1&nbsp;



 <A HREF="template.html#temp.param">temp.param</A>
 paragraph 9,</P>

<BLOCKQUOTE>
A default <I>template-argument</I> shall not be specified in a friend
template declaration.
</BLOCKQUOTE>
<P>(See also <A HREF="
     cwg_defects.html#136">issue 136</A>.)</P>
<BR>
<BR>
<HR>
<A NAME="49"></A>
<H4>49.
  
Restriction on non-type, non-value template arguments
</H4>
<B>Section: </B>14.1&nbsp;



 <A HREF="template.html#temp.param">temp.param</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>16 Oct 1998<BR>



<P>The example in
14.1&nbsp;



 <A HREF="template.html#temp.param">temp.param</A>

 paragraph
8 is:</P>
<PRE>
    template&lt;int* a&gt; struct R { /*...*/ };
    int* p;
    R&lt;p&gt; w;
</PRE>
There was a French comment was that this is an error, and there was general
agreement with that.

<P>I've been looking for the verbiage that specifies that this is an error
and haven't found it. In particular, nothing in 14.1&nbsp;



 <A HREF="template.html#temp.param">temp.param</A>
 ("Template parameters")
nor 14.3.2&nbsp;



 <A HREF="template.html#temp.arg.nontype">temp.arg.nontype</A>
 ("Template non-type arguments") appears to rule out this case.
(14.3.2&nbsp;



 <A HREF="template.html#temp.arg.nontype">temp.arg.nontype</A>
 paragraph 1 allows an argument to be "the name of an object or function with
external linkage," with no limitation on the kinds of parameters such a
name can match; "p" is, in fact, such a name.)</P>

<P>Should the resolution of the French comment include beefing up one or
both of these sections to cover the applicable rules explicitly?</P>

<P>
<B>Proposed Resolution (04/99):</B>
Change the example in 14.1&nbsp;



 <A HREF="template.html#temp.param">temp.param</A>

paragraph 8 from:</P>
<PRE>
    template&lt;int *a&gt; struct R { /* ... */ };
    template&lt;int b[5]&gt; struct S { /* ... */ };
    int *p;
    R&lt;p&gt; w; // <I>OK</I>
    S&lt;p&gt; x; // <I>OK due to parameter adjustment</I>
    int v[5];
    R&lt;v&gt; y; // <I>OK due to implicit argument conversion</I>
    S&lt;v&gt; z; // <I>OK due to both adjustment and conversion</I>
</PRE>
to:
<PRE>
    template&lt;int *a&gt; struct R { /* ... */ };
    template&lt;int b[5]&gt; struct S { /* ... */ };
    int p;
    R&lt;&amp;p&gt; w; // <I>OK</I>
    S&lt;&amp;p&gt; x; // <I>OK due to parameter adjustment</I>
    int v[5];
    R&lt;v&gt; y; // <I>OK due to implicit argument conversion</I>
    S&lt;v&gt; z; // <I>OK due to both adjustment and conversion</I>
</PRE>
Furthermore, in 14.3.2&nbsp;



 <A HREF="template.html#temp.arg.nontype">temp.arg.nontype</A>
 paragraph 1:
<UL>
<LI>the fourth bullet item should be changed from "...where the &amp; is optional
if the name refers to a function or array;" to "...where the &amp; is optional
if the name refers to a function or array, or if
the corresponding <I>template-parameter</I> is a reference;"</LI>

<LI>the third bullet item should be removed.</LI>
</UL>
<BR>
<BR>
<HR>
<A NAME="187"></A>
<H4>187.
  
Scope of template parameter names
</H4>
<B>Section: </B>14.1&nbsp;



 <A HREF="template.html#temp.param">temp.param</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>John Spicer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>15 Nov 1999<BR>





<P>At the Dublin meeting (04/99), the Committee proposed to resolve
<A HREF="
     cwg_defects.html#22">issue 22</A> by simply changing the
wording to make clear that a template parameter cannot be used in its
own default argument.  This creates a third treatment of this kind of
situation, in addition to
3.3.1&nbsp;



 <A HREF="basic.html#basic.scope.pdecl">basic.scope.pdecl</A>
 paragraph 1, where
declarators are in scope and can be used in their initializers, and
paragraph 3, where an enumerator is not in scope until after its
complete <I>enumerator-definition</I>.  The Dublin resolution is for
the template parameter to be in scope in its default argument but not
usable.  It would be more consistent to treat template parameters like
enumerators: simply not in scope until the entire
<I>template-parameter</I> declaration is seen.</P>

<P>On a related note,
14.1&nbsp;



 <A HREF="template.html#temp.param">temp.param</A>
 paragraph 14 should be
rewritten to connect the prohibition with visibility rules; otherwise,
it sounds as if the following example is not permitted:</P>

<PRE>
    const int Z = 1;
    template &lt;int X = Z, int Z&gt; class A {};
</PRE>

<P>
<B>Notes from 04/00 meeting:</B>
</P>

<P>The core working group did not reach consensus on the suggested
approach to <A HREF="
     cwg_defects.html#22">issue 22</A>.  However, it was
agreed that the intent expressed in the earlier resolution would be
better served by different wording.</P>

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>
<I>[Note: This resolution supersedes the resolution to
<A HREF="
     cwg_defects.html#22">issue 22</A>.]</I>
</P>

<P>Replace 14.1&nbsp;



 <A HREF="template.html#temp.param">temp.param</A> paragraph 14 as follows:</P>

<BLOCKQUOTE>
A template parameter shall not be used in its own default argument.
</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="30"></A>
<H4>30.
  
Valid uses of "<TT>::template</TT>"
</H4>
<B>Section: </B>14.2&nbsp;



 <A HREF="template.html#temp.names">temp.names</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Daveed Vandevoorde
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>28 May 1998<BR>





<P>I have a request for clarification regarding a issue similar to John
Wiegley's, but wrt. the <TT>::template</TT> syntax. More precisely, where
is</P>
<PRE>
    X::template Y
</PRE>
allowed? (It is required for dependent <TT>X</TT> where <TT>Y</TT> is a
<I>template-id</I>, I believe, but it doesn't seem to be disallowed elsewhere.)
    
<P>The question also holds for '<TT>.template</TT>' and '<TT>-&gt;template</TT>'.</P>
    
<P>
<B>Proposed Resolution (04/99):</B>
Append to 14.2&nbsp;



 <A HREF="template.html#temp.names">temp.names</A>
 paragraph 5:</P>
<BLOCKQUOTE>Furthermore, names of member templates shall not be prefixed
by the keyword <TT>template</TT> if the <I>postfix-expression</I> or <I>qualified-id</I>
does not appear in the scope of a template. [<I>Note:</I> just as is the case
with the <TT>typename</TT> prefix, the <TT>template</TT> prefix is allowed
in cases where it is not strictly necessary; i.e., when the expression
on the left of the <TT>-&gt;</TT> or <TT>.</TT>, or the <I>nested-name-specifier</I>
is not dependent on a <I>template-parameter</I>. ]</BLOCKQUOTE>
<BR>
<BR>
<HR>
<A NAME="38"></A>
<H4>38.
  
Explicit template arguments and operator functions
</H4>
<B>Section: </B>14.2&nbsp;



 <A HREF="template.html#temp.names">temp.names</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>John Wiegley
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>17 Aug 1998<BR>





<P>It appears from the grammar that explicit template arguments cannot
be specified for overloaded operator names. Does this mean that
template operators can never be friends?</P>
 
<P>But assuming that I read things wrong, then I should be able to
specify a global template '<TT>operator +</TT>' by writing:</P>

<PRE>
    friend A::B operator + &lt;&gt;(char&amp;);
</PRE>
<U>John Spicer:</U>

<P>You <B>should</B> be able to have explicit template arguments on operator
functions, but the grammar does seem to prohibit it (unless I'm reading
it incorrectly). This is an error in the grammar, they should be permitted.</P>

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>Change the grammar specified in 13.5&nbsp;



 <A HREF="over.html#over.oper">over.oper</A>
paragraph 1 from <BR>

<UL>
<I>operator-function-id:</I>
<UL>
<TT>operator</TT> <I>operator</I>
</UL>
</UL>

to<BR>

<UL>
<I>operator-function-id:</I>
<UL>
<TT>operator</TT> <I>operator</I>
<BR>
<TT>operator</TT> <I>operator</I> <TT>&lt;</TT>
<I>template-argument-list<SUB>opt</SUB></I> <TT>&gt;</TT>
</UL>
</UL>
</P>
<BR>
<BR>
<HR>
<A NAME="100"></A>
<H4>100.
  
Clarify why string literals are not allowed as template arguments
</H4>
<B>Section: </B>14.3.2&nbsp;



 <A HREF="template.html#temp.arg.nontype">temp.arg.nontype</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>9 Mar 1999<BR>



<P>The explanation in
14.3.2&nbsp;



 <A HREF="template.html#temp.arg.nontype">temp.arg.nontype</A>

paragraph 2 of why a string literal cannot be
used as a template argument leaves something to be desired:</P>
<BLOCKQUOTE>
...because a string literal is an object with internal linkage.
</BLOCKQUOTE>
I can't find anything that says that a string literal has
internal linkage.  In fact, I'd be pretty surprised if I did,
since linkage is defined (in
3.5&nbsp;



 <A HREF="basic.html#basic.link">basic.link</A>
) strictly in terms of
names, and a string literal doesn't have a name.

Actually, I think that it's the namelessness of a string literal
that prevents it from being a template argument; only the
third and fourth bullets of
14.3.2&nbsp;



 <A HREF="template.html#temp.arg.nontype">temp.arg.nontype</A>

paragraph 1 could conceivably apply,
and both of those require that the entity have a name (i.e.,
that they be given as an <I>id-expression</I>).

<P>
<B>Proposed Resolution (10/99):</B>
In 14.3.2&nbsp;



 <A HREF="template.html#temp.arg.nontype">temp.arg.nontype</A>
 paragraph 2, change</P>

<BLOCKQUOTE>
[<I>Note:</I> a string literal
(2.13.4&nbsp;



 <A HREF="lex.html#lex.string">lex.string</A>
) is not an acceptable
<I>template-argument</I> because a string literal is an object
with internal linkage.
</BLOCKQUOTE>

to

<BLOCKQUOTE>
[<I>Note:</I> a string literal
(2.13.4&nbsp;



 <A HREF="lex.html#lex.string">lex.string</A>
) does not satisfy the
requirements of  any of these categories and thus is not an
acceptable <I>template-argument</I>.
</BLOCKQUOTE>
<BR>
<BR>
<HR>
<A NAME="249"></A>
<H4>249.
  
What is a member function template?
</H4>
<B>Section: </B>14.5.1.1&nbsp;



 <A HREF="template.html#temp.mem.func">temp.mem.func</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>David Thornley
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>11 Oct 2000<BR>


<P>The phrase "member function template" is used in
3.2&nbsp;



 <A HREF="basic.html#basic.def.odr">basic.def.odr</A> paragraph 5 in the list of entities whose
definitions can appear more than once in a program, with a
cross-reference to 14.5.1.1&nbsp;



 <A HREF="template.html#temp.mem.func">temp.mem.func</A>.  The title of
that section is "Member functions of class templates," and paragraph 1
of that section says,</P>

<BLOCKQUOTE>

A member function template may be defined outside of the class
template in which it is declared.

</BLOCKQUOTE>

<P>The example in that paragraph shows a non-template member function
of a class template being defined.  This gives the impression that the
phrase "member function template" is intended to refer to a member
function of a class template.</P>

<P>If this usage were intended, much of the rest of the Standard
would be unintelligible: objects of class template specializations
could not be copied (12.8&nbsp;



 <A HREF="special.html#class.copy">class.copy</A> paragraph 3),
member functions of class templates could not be declared
<TT>virtual</TT> (14.5.2&nbsp;



 <A HREF="template.html#temp.mem">temp.mem</A> paragraph 3),
etc.</P>

<P>
<B>Suggested resolution:</B>
</P>

<P>Change "member function template" to "member function of a class
template" in both 3.2&nbsp;



 <A HREF="basic.html#basic.def.odr">basic.def.odr</A> paragraph 5 and
14.5.1.1&nbsp;



 <A HREF="template.html#temp.mem.func">temp.mem.func</A> paragraph 1.</P>

<P>(See also <A HREF="
     cwg_active.html#205">issue 205</A>.)</P>

<P>
<B>Proposed resolution (10/00):</B> As suggested.</P>

<BR>
<BR>
<HR>
<A NAME="116"></A>
<H4>116.
  
Equivalent and functionally-equivalent function templates
</H4>
<B>Section: </B>14.5.5.1&nbsp;



 <A HREF="template.html#temp.over.link">temp.over.link</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>11 May 1999<BR>





<P>14.5.5.1&nbsp;



 <A HREF="template.html#temp.over.link">temp.over.link</A>
, paragraphs 5 and 6,
describes equivalence and
functional equivalence for expressions involving template
parameters.  As a note in paragraph 5 points out, such
expressions may involve type parameters as well as non-type
parameters.</P>

<P>Paragraph 7, however, describes the equivalence of function
templates only with respect to non-type template parameters.
It appears to be unspecified how to determine the equivalence
of template functions whose types involve expressions that
use template type parameters.</P>

<PRE>
    template &lt;int I&gt; struct S { };

    // The following two declarations are equivalent:
    template &lt;int I&gt; void f(S&lt;I&gt;);
    template &lt;int J&gt; void f(S&lt;J&gt;);

    // The IS doesn't say whether these are equivalent:
    template &lt;class T&gt; void f(S&lt;sizeof(T)&gt;);
    template &lt;class T&gt; void f(S&lt;sizeof(T)&gt;);
</PRE>

<P>
<B>Proposed resolution (10/99):</B>
Remove the three uses of the words "non-type" in
14.5.5.1&nbsp;



 <A HREF="template.html#temp.over.link">temp.over.link</A>
 paragraph 7.</P>
<BR>
<BR>
<HR>
<A NAME="120"></A>
<H4>120.
  
Nonexistent non-terminal <I>qualified-name</I>
</H4>
<B>Section: </B>14.6&nbsp;



 <A HREF="template.html#temp.res">temp.res</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Bill Gibbons
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>28 May 1999<BR>



<P>In 14.6&nbsp;



 <A HREF="template.html#temp.res">temp.res</A>
, references to the
nonexistent syntactic non-terminal <I>qualified-name</I> occur twice
in paragraph 3, twice in paragraph 4, and once in paragraph 5.  There
is also a reference in
14.1&nbsp;



 <A HREF="template.html#temp.param">temp.param</A>
 paragraph 2.</P>

<P>
<B>Proposed resolution (10/99):</B> Change
the reference in all these cases to <I>qualified-id</I>.</P>
<BR>
<BR>
<HR>
<A NAME="121"></A>
<H4>121.
  
Dependent type names with non-dependent <I>nested-name-specifier</I>s
</H4>
<B>Section: </B>14.6&nbsp;



 <A HREF="template.html#temp.res">temp.res</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Bill Gibbons
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>28 May 1999<BR>



<P>The wording in
14.6&nbsp;



 <A HREF="template.html#temp.res">temp.res</A>
 paragraph 3:</P>
<BLOCKQUOTE>
A <I>qualified-name</I> that refers to a type and that depends on a
<I>template-parameter</I>
(14.6.2&nbsp;



 <A HREF="template.html#temp.dep">temp.dep</A>
) shall be prefixed by the keyword
<TT>typename</TT>
to indicate that the <I>qualified-name</I> denotes a type, forming an
elaborated-type-specifier
(7.1.5.3&nbsp;



 <A HREF="dcl.html#dcl.type.elab">dcl.type.elab</A>
).
</BLOCKQUOTE>

was intended to say:
<BLOCKQUOTE>
A <I>qualified-id</I> that refers to a type and in which the
<I>nested-name-specifier</I> depends on a <I>template-parameter</I>
(14.6.2&nbsp;



 <A HREF="template.html#temp.dep">temp.dep</A>
) shall ...
</BLOCKQUOTE>

in much the same vein as
14.6.2.1&nbsp;



 <A HREF="template.html#temp.dep.type">temp.dep.type</A>, second bullet, first half.

<P>
<B>Proposed resolution (10/00):</B> As suggested.</P>
<BR>
<BR>
<HR>
<A NAME="183"></A>
<H4>183.
  
<TT>typename</TT> in explicit specializations
</H4>
<B>Section: </B>14.6&nbsp;



 <A HREF="template.html#temp.res">temp.res</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>John Spicer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>9 Nov 1999<BR>





<P>
<U>John Spicer</U>:
In 14.6&nbsp;



 <A HREF="template.html#temp.res">temp.res</A>
 paragraph 5, 
the standard says</P>

<BLOCKQUOTE>
The keyword <TT>typename</TT> shall only be used in
template declarations and definitions...
</BLOCKQUOTE>

My understanding of the intent of this restriction is to say that
<TT>typename</TT> is only allowed in contexts in which template
dependent names can be found, but the wording leaves open to
interpretation whether <TT>typename</TT> is allowed in an explicit
specialization, such as:

<PRE>
    template &lt;class T&gt; struct A {};
    template &lt;class T&gt; struct B { typedef int X; };
    template &lt;&gt; struct A&lt;int&gt; {
        typename B&lt;int&gt;::X x;
    };
</PRE>

My understanding is that such usage is not permitted.
This should be clarified one way or the other.

<P>
<U>Mike Miller</U>:
I agree with your understanding that you are not allowed to
use <TT>typename</TT> in an explicit specialization.  However, I think
the standard already says that &mdash; an explicit specialization
is not a template declaration.  According to the grammar in
14&nbsp;



 <A HREF="template.html#temp">temp</A>
 paragraph 1, a
<I>template-declaration</I> must have a non-empty
<I>template-parameter-list</I>.</P>

<P>
<U>Nathan Myers</U>:
Is there any actual reason for this restriction?  Its only apparent
effect is to make it harder to specialize templates, with no
corresponding benefit.</P>

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>In 14.6&nbsp;



 <A HREF="template.html#temp.res">temp.res</A> paragraph 5, replace</P>

<BLOCKQUOTE>

The keyword <TT>typename</TT> shall only be applied to qualified
names, but those names need not be dependent.

</BLOCKQUOTE>

<P>with</P>

<BLOCKQUOTE>

The keyword <TT>typename</TT> shall be applied only to qualified
names, but those names need not be dependent.  The keyword
<TT>typename</TT> shall be used only in contexts in which dependent
names can be used.  This includes template declarations and
definitions but excludes explicit specialization declarations and
explicit instantiation declarations.

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="213"></A>
<H4>213.
  
Lookup in dependent base classes
</H4>
<B>Section: </B>14.6.2&nbsp;



 <A HREF="template.html#temp.dep">temp.dep</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>John Spicer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>10 Mar 2000<BR>




<P>Paragraphs 3-4 of 14.6.2&nbsp;



 <A HREF="template.html#temp.dep">temp.dep</A> say, in part,</P>

<BLOCKQUOTE>

if a base class of [a class] template depends on a
<I>template-parameter</I>, the base class scope is not examined during
name lookup until the class template is instantiated...  If a base
class is a dependent type, a member of that class cannot hide a name
declared within a template, or a name from the template's enclosing
scope.

</BLOCKQUOTE>

<P>
<U>John Spicer</U>: The wording in paragraph 4 seems particularly
odd to me.  It essentially changes the order in which scopes are
considered.  If a scope outside of the template declares a given name,
that declaration hides entities of the same name from template
dependent base classes (but not from nondependent base classes).</P>

<P>In the following example, the calls of <TT>f</TT> and <TT>g</TT>
are handled differently because <TT>B::f</TT> cannot hide
<TT>::f</TT>, but <TT>B::g</TT> doesn't try to hide anything, so it
can be called.</P>

<PRE>
    extern "C" int printf(char *, ...);
    template &lt;class T&gt; struct A : T {
        void h(T t) {
            f(t);  // calls ::f(B)
            g(t);  // calls B::g
        }
    };

    struct B {
        void f(B){printf("%s", "in B::f\n");}
        void g(B){printf("%s", "in B::g\n");}
    };

    void f(B){printf("%s", "in ::f\n");}

    int main()
    {
        A&lt;B&gt; ab;
        B b;
        ab.h(b);
    }
</PRE>

<P>I don't think the current wording in the standard provides a useful
facility.  The author of class <TT>A</TT> can't be sure that a given
call is going to call a base class function unless the base class is
explicitly specified.  Adding a new global function could cause the
program to suddenly change meaning.</P>

<P>What I <I>thought</I> the rule was is, "If a base class is a
dependent type a member of that class is not found by unqualified
lookup".</P>

<P>
<U>Derek Inglis:</U> My understanding is the same except that I'd
remove the word "qualified" from your sentence.</P>

<P>
<U>Erwin Unruh</U>: My interpretation is based on 14.6.4&nbsp;



 <A HREF="template.html#temp.dep.res">temp.dep.res</A> and especially 14.6.4.2&nbsp;



 <A HREF="template.html#temp.dep.candidate">temp.dep.candidate</A> (and
largely on my memory of the discussions). For all unqualified names
you do something like the following algorithm:</P>

<OL>
<LI>check whether it is a dependent function call</LI>
<LI>Do a lookup in the definition context and remember what you found there</LI>
<LI>Do a Koenig-Lookup at instantiation time</LI>
<LI>perform overloading if necessary</LI>
</OL>

<P>Regarding names from base classes you cannot find them in 2) because you
don't know what base class you have. You cannot find them in 3) because
members of classes are not found by Koenig lookup (only namespaces are
considered). So you don't find them at all (for unqualified names).</P>

<P>For a qualified name, you start lookup for each 'part' of the qualification.
Once you reach a dependent part, you stop and continue lookup at the
instantiation point. For example:</P>

<PRE>
    namespace A {
      namepace B {
	template &lt;class T&gt; class C {
	  template &lt;class U&gt; class D {
	    typedef int E;
	    // ...
	  };
	};
      };
    };

    template &lt;class T&gt; class F : public T {
      typename A::B::C&lt;int&gt;::D&lt;T&gt;::E var1;
      typename A::B::C&lt;T&gt;::D&lt;int&gt;::E var2;
      typename F::T::X var3;
    }
</PRE>

<P>For <TT>var1</TT> you do lookup for <TT>A::B::C&lt;int&gt;::D</TT>
at definition time, for <TT>var2</TT> you only do lookup for
<TT>A::B::C</TT>. The rest of the lookup is done at instantiation time
since specialisations could change part of the lookup. Similarly the
lookup for <TT>var3</TT> stops after <TT>F::T</TT> at definition
time.</P>

<P>My impression was that an unqualified name never refers to a name
in a dependent base class.</P>

<P>(See also <A HREF="
     cwg_defects.html#197">issue 197</A>.)</P>

<P>
<B>Proposed resolution (10/00):</B>
</P>

<OL>

<LI>

<P>In 14.6.2&nbsp;



 <A HREF="template.html#temp.dep">temp.dep</A> paragraph 3, replace</P>

<BLOCKQUOTE>

In the definition of a class template or in the definition of a member
of such a template that appears outside of the template definition, if
a base class of this template depends on a <I>template-parameter</I>,
the base class scope is not examined during name lookup until the
class template is instantiated.

</BLOCKQUOTE>

<P>with</P>

<BLOCKQUOTE>

In the definition of a class template or a member of a class template,
if a base class of the class template depends on a
<I>template-parameter</I>, the base class scope is not examined during
unqualified name lookup either at the point of definition of the class
template or member or during an instantiation of the class template or
member.

</BLOCKQUOTE>

</LI>

<LI>

<P>Remove from 14.6.2&nbsp;



 <A HREF="template.html#temp.dep">temp.dep</A> paragraph 4:</P>

<BLOCKQUOTE>

If a base class is a dependent type, a member of that class cannot
hide a name declared within a template, or a name from the template's
enclosing scopes.

</BLOCKQUOTE>

</LI>

</OL>

<BR>
<BR>
<HR>
<A NAME="108"></A>
<H4>108.
  
Are classes nested in templates dependent?
</H4>
<B>Section: </B>14.6.2.1&nbsp;



 <A HREF="template.html#temp.dep.type">temp.dep.type</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mark Mitchell
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>14 Apr 1999<BR>





<P>
<U>Mark Mitchell (via John Spicer):</U> Given:</P>
<PRE>
  template &lt;class T&gt; struct S {
     struct I1 {
       typedef int X;
     };
     struct I2 : public I1 {
        X x;
     };
  };
</PRE>
<P>Is this legal?  The question really boils down to asking whether or
not <TT>I1</TT> is a dependent type.  On the one hand, it doesn't seem to fit
any of the qualifications in 14.6.2.1&nbsp;



 <A HREF="template.html#temp.dep.type">temp.dep.type</A>
.
On the other, 14.7.3&nbsp;



 <A HREF="template.html#temp.expl.spec">temp.expl.spec</A>
 allows
explicit specialization of a member class of a class template, so something
like:</P>
<PRE>
  template &lt;&gt; 
  struct S&lt;double&gt;::I1 {
     int X;
  };
</PRE>
<P>is apparently legal.  But, then, `X' no longer refers to a type name.
So, it seems like `I1' should be classified as dependent.  What am I
missing?</P>

<P>
<U>Erwin Unruh:</U> I wrote that particular piece of text and I just
missed the problem above. It is intended to be a dependent type. The
reasoning is that <TT>I1</TT> is just a shorthand for
<TT>S&lt;T&gt;::I1</TT> which clearly is
dependent.</P>

<P>
<B>Suggested Resolution:</B> (Erwin Unruh)</P>
<P>I think the list of what is a dependent type should be extended to cover
"a type declared and used within the same template" modulo of
phrasing.</P>

<P>(See also paper J16/00-0009 = WG21 N1231.  This issue is also
somewhat related to <A HREF="
     cwg_active.html#205">issue 205</A>: classes
nested inside template classes are, in some sense, "templates," just
as non-template member functions of class templates and static data
members of class templates are "templates.")</P>

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>Add after 14.6.1&nbsp;



 <A HREF="template.html#temp.local">temp.local</A> paragraph 2:</P>

<BLOCKQUOTE>

Within the scope of a class template, when the unqualified name of a
nested class of the class template is referred to, it is equivalent to
the name of the nested class qualified by the name of the enclosing
class template. [<I>Example:</I>

<PRE>
    template &lt;class T&gt; struct A {
	class B {};
	// B is equivalent to A::B, which is equivalent to A&lt;T&gt;::B,
	// which is dependent.
	class C : B { };
    };
</PRE>

&mdash;<I>end example</I>] 

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="206"></A>
<H4>206.
  
Semantic constraints on non-dependent names
</H4>
<B>Section: </B>14.6.3&nbsp;



 <A HREF="template.html#temp.nondep">temp.nondep</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>23 Feb 2000<BR>


<P>At what point are semantic constraints applied to uses of
non-dependent names in template definitions?  According to
14.6.3&nbsp;



 <A HREF="template.html#temp.nondep">temp.nondep</A>
, such names are looked up
and bound at the point at which they are used, i.e., the point of
definition and not the point of instantiation.  However, the text does
not mention the checking of semantic constraints.</P>

<P>Contrast this omission with the treatment of names in default
argument expressions given in
8.3.6&nbsp;



 <A HREF="decl.html#dcl.fct.default">dcl.fct.default</A>
 paragraph 5, where
the treatment of semantic constraints is explicit:</P>

<BLOCKQUOTE>
The names in the expression are bound, and the semantic constraints
are checked, at the point where the default argument expression
appears.
</BLOCKQUOTE>

The following code is an example of where this distinction matters:

<PRE>
    struct S;

    template &lt;class T&gt; struct Q {
        S s;    // incomplete type if semantic constraints
                // are applied in the definition context
    };

    struct S { };

    // Point of instantiation of Q&lt;int&gt;; S is complete here

    Q&lt;int&gt; si;        
</PRE>

There is real-world code that depends on late checking of semantic
constraints.  The Standard should be explicit about whether this code
is broken or not.

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>In 14.6&nbsp;



 <A HREF="template.html#temp.res">temp.res</A> paragraph 7, add the following
immediately preceding the note:</P>

<BLOCKQUOTE>

If a type used in a non-dependent name is incomplete at the point at
which a template is defined but is complete at the point at which an
instantiation is done, and if the completeness of that type affects
whether or not the program is well-formed or affects the semantics of
the program, the program is ill-formed; no diagnostic is required.

</BLOCKQUOTE>

<BR>
<BR>
<HR>
<A NAME="22"></A>
<H4>22.
  
Template parameter with a default argument that refers to itself
</H4>
<B>Section: </B>14.6.4&nbsp;



 <A HREF="template.html#temp.dep.res">temp.dep.res</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>unknown
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>unknown<BR>





<P>14.1&nbsp;



 <A HREF="template.html#temp.param">temp.param</A>
 paragraph 13 says:</P>
<BLOCKQUOTE>The scope of a <I>template-parameter</I> extends from its point of
declaration until the end of its template. In particular, a <I>template-parameter</I>
can be used in the declaration of subsequent <I>template-parameter</I>s and their
default arguments.</BLOCKQUOTE>
Is the following well-formed?
<PRE>
    template&lt;class U = U&gt; class X { ... };
</PRE>

<P>
<I>[Note: this issue is resolved by the resolution of
<A HREF="
     cwg_defects.html#187">issue 187</A>.]</I>
</P>
<BR>
<BR>
<HR>
<A NAME="24"></A>
<H4>24.
  
Errors in examples in 14.7.3
</H4>
<B>Section: </B>14.7.3&nbsp;



 <A HREF="template.html#temp.expl.spec">temp.expl.spec</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>unknown
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>unknown<BR>





<P>
<B>Problem Description:</B>
At least four of the examples in 14.7.3&nbsp;



 <A HREF="template.html#temp.expl.spec">temp.expl.spec</A>
 have errors. </P>

<P>
<B>Proposed Resolution (10/99):</B>
</P>

<P>1. Change the example in paragraph 8 from: </P>
<BLOCKQUOTE>
[<I>Example:</I>
<PRE>
    // <I>file #1 </I>
    #include &lt;vector&gt; 
    // <I>Primary class template</I> vector
    export template&lt;class T&gt; void f(t) { 
        vector&lt;T&gt; vec;         // <I>should match the specialization</I>
        /* ... */ 
    } 

    // <I>file #2 </I>
    #include &lt;vector&gt; 
    class B { }; 
    // <I>Explicit specialization of </I>vector<I> for </I>vector&lt;B&gt;
    template&lt;class T&gt; class vector&lt;B&gt; { /* ... */ } 
    template&lt;class T&gt; void f(T); 
    void g(B b) { 
        f(b);                   // <I>ill formed: </I>
                                // f&lt;B&gt; <I>should refer to </I>vector&lt;B&gt;<I>, but the </I>
                                // <I>specialization was not declared with the </I>
                                // <I>definition of </I>f<I> in file #1 </I>
    } 
</PRE>
<I>&mdash;end example</I>]
</BLOCKQUOTE>
to: 
<BLOCKQUOTE>
[<I>Example: </I>
<PRE>
    // <I>file #1 </I>
    #include &lt;vector&gt; 
    // <I>Primary class template</I> vector
    export template&lt;class T&gt; void f(T) { 
        std::vector&lt;T&gt; vec;     // <I>should match the specialization </I>
        /* ... */ 
    }; 

    // <I>file #2 </I>
    #include &lt;vector&gt; 
    class B { }; 
    // <I>Explicit specialization of </I>vector<I> for </I>vector&lt;B&gt;
    namespace std { 
        template&lt;&gt; class vector&lt;B&gt; { /* ... */ }; 
    } 
    template&lt;class T&gt; void f(T); 
    void g(B b) { 
        f(b);                   // <I>ill formed: </I>
                                // f&lt;B&gt; <I>should refer to </I>vector&lt;B&gt;<I>, but the </I>
                                // <I>specialization was not declared with the </I>
                                // <I>definition of </I>f<I> in file #1 </I>
    } 
</PRE>
    <I>&mdash;end example</I>] 
</BLOCKQUOTE>

<P>2. The example in paragraph 16 as it appears in the IS: </P>
<BLOCKQUOTE>
[<I>Example: </I>
<PRE>
    template&lt;class T&gt; struct A { 
        void f(T); 
        template&lt;class X&gt; void g(T, X); 
        void h(T) { } 
    }; 

    // <I>specialization </I>
    template&lt;&gt; void A&lt;int&gt;::f(int); 

    // <I>out of class member template definition </I>
    template&lt;class T&gt; template&lt;class X&gt; void A&lt;T&gt;::g(T,X) { } 

    // <I>member template partial specialization </I>
    template&lt;&gt; template&lt;class X&gt; void A&lt;int&gt;::g(int, X); 

    // <I>member template specialization </I>
    template&lt;&gt; template&lt;&gt; 
        void A&lt;int&gt;::g(int, char);        // X <I>deduced as</I> char
    template&lt;&gt; template&lt;&gt; 
        void A&lt;int&gt;::g&lt;char&gt;(int, char);  // X <I>specified as</I> char

    // <I>member specialization even if defined in class definition </I>
    template&lt;&gt; void A&lt;int&gt;::h(int) { } 
</PRE>
&mdash;<I>end example</I>] 
</BLOCKQUOTE>

The word 'partial' in the third comment in the example
should be removed because this example does not illustrate partial
specialization.  Also, the two specializations of <TT>template&lt;&gt;
template&lt;&gt; void A&lt;int&gt;::g(int, char);</TT> violate
14.7&nbsp;



 <A HREF="template.html#temp.spec">temp.spec</A>
, paragraph 5, which reads:

<BLOCKQUOTE>
No program shall explicitly instantiate any template more than once,
both explicitly instantiate and explicitly specialize a template, or
specialize a template more than once for a given set of
<I>template-argument</I>s.  An implementation is not required
to diagnose a violation of this rule.
</BLOCKQUOTE>

<B>Proposed resolution (10/99): </B>
<BLOCKQUOTE>
[<I>Example: </I>
<PRE>
    template&lt;class T&gt; struct A { 
        void f(T); 
        template&lt;class X1&gt; void g1(T, X1); 
        template&lt;class X2&gt; void g2(T, X2); 
        void h(T) { } 
    }; 

    // <I>specialization </I>
    template&lt;&gt; void A&lt;int&gt;::f(int); 

    // <I>out of class member template definition </I>
    template&lt;class T&gt; template&lt;class X1&gt; void A&lt;T&gt;::g1(T,X1) { } 

    // <I>member template specialization </I>
    template&lt;&gt; template&lt;class X1&gt; void A&lt;int&gt;::g1(int, X1); 

    // <I>member template specialization </I>
    template&lt;&gt; template&lt;&gt; 
        void A&lt;int&gt;::g1(int, char);        // X1 <I>deduced as</I> char 
    template&lt;&gt; template&lt;&gt; 
        void A&lt;int&gt;::g2&lt;char&gt;(int, char);  // X2 <I>specified as</I> char 

    // <I>member specialization even if defined in class definition </I>
    template&lt;&gt; void A&lt;int&gt;::h(int) { } 
</PRE>
&mdash;<I>end example</I>] 
</BLOCKQUOTE>

<P>3. Remove the spurious semicolon (or the curly brackets) from the
end of the last line in the example in paragraph 17.  This is the
example as it appears in the IS:</P>

<BLOCKQUOTE>
[<I>Example: </I>
<PRE>
    template&lt;class T1&gt; class A { 
        template&lt;class T2&gt; class B { 
            void mf(); 
        };
    };
    template&lt;&gt; template&lt;&gt; A&lt;int&gt;::B&lt;double&gt; { };
    template&lt;&gt; template&lt;&gt; void A&lt;char&gt;::B&lt;char&gt;::mf() {};
</PRE>
&mdash;<I>end example</I>]
</BLOCKQUOTE>

<B>Proposed resolution (10/99):</B>

<BLOCKQUOTE>
[<I>Example: </I>
<PRE>
    template&lt;class T1&gt; class A { 
        template&lt;class T2&gt; class B { 
            void mf(); 
        };
    };
    template&lt;&gt; template&lt;&gt; A&lt;int&gt;::B&lt;double&gt;;
    template&lt;&gt; template&lt;&gt; void A&lt;char&gt;::B&lt;char&gt;::mf();
</PRE>
&mdash;<I>end example</I>]
</BLOCKQUOTE>
<P>
<I>Note (Steve Adamczyk, March 2002): that's still incorrect.  The missing
"<TT>class</TT>" was added editorially when TC1 was prepared.</I>
</P>

<P>4. Remove spurious semicolons (or curly brackets) from the
specializations of <TT>mf1</TT> and <TT>mf2</TT> in the example in
paragraph 18.  This is the text of the example as it appears in the
IS:</P>

<BLOCKQUOTE>
[<I>Example: </I>
<PRE>
    template&lt;class T1&gt; class A { 
        template&lt;class T2&gt; class B { 
            template&lt;class T3&gt; void mf1(T3); 
            void mf2(); 
        }; 
    }; 
    template&lt;&gt; template&lt;class X&gt; 
        class A&lt;int&gt;::B { }; 
    template&lt;&gt; template&lt;&gt; template&lt;class T&gt; 
        void A&lt;int&gt;::B&lt;double&gt;::mf1(T t) { }; 
    template&lt;class Y&gt; template&lt;&gt; 
        void A&lt;Y&gt;::B&lt;double&gt;::mf2() { }; // <I>ill-formed; </I>B&lt;double&gt;<I> is specialized but </I>
                                         // <I>its enclosing class template </I>A<I> is not </I>
</PRE>
&mdash;<I>end example</I>] 
</BLOCKQUOTE>

<B>Proposed resolution (10/99):</B>
<BLOCKQUOTE>
[<I>Example: </I>
<PRE>
    template&lt;class T1&gt; class A { 
        template&lt;class T2&gt; class B { 
            template&lt;class T3&gt; void mf1(T3); 
            void mf2(); 
        }; 
    }; 
    template&lt;&gt; template&lt;class X&gt; 
        class A&lt;int&gt;::B { }; 
    template&lt;&gt; template&lt;&gt; template&lt;class T&gt; 
        void A&lt;int&gt;::B&lt;double&gt;::mf1(T t) { }
    template&lt;class Y&gt; template&lt;&gt; 
        void A&lt;Y&gt;::B&lt;double&gt;::mf2() { } // <I>ill-formed; </I>B&lt;double&gt;<I> is specialized but </I>
                                         // <I>its enclosing class template </I>A<I> is not </I>
</PRE>
&mdash;<I>end example</I>] 
</BLOCKQUOTE>
<P>
<I>Note (Steve Adamczyk, March 2002): that's still incorrect.
See <A HREF="
     cwg_defects.html#336">issue 336</A>.</I>
</P>
<BR>
<BR>
<HR>
<A NAME="64"></A>
<H4>64.
  
Partial ordering to disambiguate explicit specialization
</H4>
<B>Section: </B>14.7.3&nbsp;



 <A HREF="template.html#temp.expl.spec">temp.expl.spec</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Steve Adamczyk
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>13 Oct 1998<BR>



<P>Paragraph 12 should address partial ordering. It wasn't updated
when that change was made and conflicts with
14.5.5.2&nbsp;



 <A HREF="template.html#temp.func.order">temp.func.order</A>
 paragraph 1.</P>

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>Remove
14.7.3&nbsp;



 <A HREF="template.html#temp.expl.spec">temp.expl.spec</A>
 paragraph 12 and the
example that follows.</P>
<BR>
<BR>
<HR>
<A NAME="241"></A>
<H4>241.
  
Error in example in 14.8.1
</H4>
<B>Section: </B>14.8.1&nbsp;



 <A HREF="template.html#temp.arg.explicit">temp.arg.explicit</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>9 Aug 2000<BR>


<P>14.8.1&nbsp;



 <A HREF="template.html#temp.arg.explicit">temp.arg.explicit</A> paragraph 6 contains the following
example:</P>

<PRE>
    namespace A {
        struct B { };
        template&lt;int X&gt; void f();
    }
    namespace C {
        template&lt;class T&gt; void f(T t);
    }
    void g(A::B b) {
        f&lt;3&gt;(b);    // ill-formed: not a function call
        A::f&lt;3&gt;(b); // well-formed
        C::f&lt;3&gt;(b); // ill-formed; argument dependent lookup
                    // only applies to unqualified names
        using C::f;
        f&lt;3&gt;(b);    // well-formed because C::f is visible; then
                    // A::f is found by argument dependent lookup
    }
</PRE>

<P>
<TT>A::f()</TT> should have a parameter of type <TT>A::B</TT>.</P>

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>In the example in 14.8.1&nbsp;



 <A HREF="template.html#temp.arg.explicit">temp.arg.explicit</A> paragraph 6,
change the third line from</P>

<PRE>
        template &lt;int X&gt; void f();
</PRE>

<P>to</P>

<PRE>
        template &lt;int X&gt; void f(B);
</PRE>

<BR>
<BR>
<HR>
<A NAME="181"></A>
<H4>181.
  
Errors in template <I>template-parameter</I> example
</H4>
<B>Section: </B>14.8.2.5&nbsp;



 <A HREF="template.html#temp.deduct.type">temp.deduct.type</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>John Spicer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>4 Nov 1999<BR>





<P>14.8.2.5&nbsp;



 <A HREF="template.html#temp.deduct.type">temp.deduct.type</A>
 paragraph 18 uses
incorrect syntax.  Instead of</P>

<PRE>
    template &lt;template X&lt;class T&gt; &gt; struct A { };
    template &lt;template X&lt;class T&gt; &gt; void f(A&lt;X&gt;) { }
</PRE>

it should be

<PRE>
    template &lt;template &lt;class T&gt; class X&gt; struct A { };
    template &lt;template &lt;class T&gt; class X&gt; void f(A&lt;X&gt;) { }
</PRE>

<P>
<B>Proposed resolution (10/00):</B> As suggested.</P>

<P>
<I>[Note: this section was numbered 14.8.2.4 in ISO/IEC 14882:2003.]</I>
</P>
<BR>
<BR>
<HR>
<A NAME="98"></A>
<H4>98.
  
Branching into try block
</H4>
<B>Section: </B>15&nbsp;



 <A HREF="except.html#except">except</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Jack Rouse
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>23 Feb 1999<BR>



<P>At the top of clause 15, in paragraph 2, it says:</P>
<BLOCKQUOTE>
A <TT>goto</TT>, <TT>break</TT>, <TT>return</TT>, or <TT>continue</TT> statement can be used to transfer
control out of a try block or handler, but not into one.
</BLOCKQUOTE>
What about <TT>switch</TT> statements?
<PRE>
    switch ( f() )
    {
    case 1:
         try {
             g();
    case 2:
             h();
         }
         catch (...)
         {
             // handler
         }
    break;
    }
</PRE>

<B>Daveed Vandevoorde:</B>

<P>Consider:</P>
<PRE>
    void f() {
        try {
        label:
            ;
        } catch(...) {
            goto label;
        }
    }
</PRE>

Now the phrase "try block" (without a hyphen) is used in paragraph
1 in a way that causes me to think that it is not intended to
include the corresponding handlers. On the other hand, the grammar
entity "<I>try-block</I>" (with hyphen) does include the handlers.

So is the intent to prohibit the above or not?

<P>
<B>Proposed resolution (10/00:</B>
</P>

<P>Change text in 15&nbsp;



 <A HREF="except.html#except">except</A> paragraph 2 from:</P>

<BLOCKQUOTE>A <TT>goto</TT>, <TT>break</TT>, <TT>return</TT>, or
<TT>continue</TT> statement
can be used to transfer control out of a try block or handler, but not
into one.
</BLOCKQUOTE>
to:
<BLOCKQUOTE>
A <TT>goto</TT> or <TT>switch</TT> statement shall not be used
to transfer control into a try block or into a handler.
<BR>[ <I>Example:</I>
<BLOCKQUOTE>
<TT>void f() {</TT>
<BR>
<TT>&nbsp; goto l1;&nbsp; // Ill-formed</TT>
<BR>
<TT>&nbsp; goto l2;&nbsp; // Ill-formed</TT>
<BR>
<TT>&nbsp; try {</TT>
<BR>
<TT>&nbsp;&nbsp;&nbsp; goto l1;&nbsp; // OK</TT>
<BR>
<TT>&nbsp;&nbsp;&nbsp; goto l2;&nbsp; // Ill-formed</TT>
<BR>
<TT>&nbsp;&nbsp;&nbsp; l1: ;</TT>
<BR>
<TT>&nbsp; } catch (...) {</TT>
<BR>
<TT>&nbsp;&nbsp;&nbsp; l2: ;</TT>
<BR>
<TT>&nbsp;&nbsp;&nbsp; goto l1;&nbsp; // Ill-formed</TT>
<BR>
<TT>&nbsp;&nbsp;&nbsp; goto l2;&nbsp; // OK</TT>
<BR>
<TT>&nbsp; }</TT>
<BR>
<TT>}</TT>
</BLOCKQUOTE>
&mdash;<I>end example</I> ]
<BR>A <TT>goto</TT>, <TT>break</TT>, <TT>return</TT>, or <TT>continue</TT>
statement can be used to transfer control out of a try block or handler.
</BLOCKQUOTE>

<P>(See also <A HREF="
     cwg_defects.html#246">issue 246</A>.)</P>

<BR>
<BR>
<HR>
<A NAME="210"></A>
<H4>210.
  
What is the type matched by an exception handler?
</H4>
<B>Section: </B>15.3&nbsp;



 <A HREF="except.html#except.handle">except.handle</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Scott Douglass
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>6 Mar 2000<BR>



<P>15.3&nbsp;



 <A HREF="except.html#except.handle">except.handle</A> paragraph 3 says,</P>

<BLOCKQUOTE>

A <I>handler</I> is a match for a <I>throw-expression</I> with an
object of type <TT>E</TT>...

</BLOCKQUOTE>

<P>This wording leaves it unclear whether it is the dynamic type of the
object being thrown or the static type of the expression that
determines whether a handler is a match for a given exception.  For
instance,</P>

<PRE>
    struct B { B(); virtual ~B(); };
    struct D : B { D(); };
    void toss(const B* b) { throw *b; }
    void f() { const D d; toss(&amp;d); }
</PRE>

<P>In this code, presumably the type to be matched is <TT>B</TT> and not
<TT>const D</TT> (15.1&nbsp;



 <A HREF="except.html#except.throw">except.throw</A>).</P>

<P>
<B>Suggested resolution:</B> Replace the cited wording as follows:</P>

<BLOCKQUOTE>

A <I>handler</I> is a match for a <I>throw-expression</I> which
initialized a temporary (15.1&nbsp;



 <A HREF="except.html#except.throw">except.throw</A>) of type
<TT>E</TT>...

</BLOCKQUOTE>

<P>
<B>Proposed resolution (10/00):</B>
</P>

<OL>

<LI>
<P>Change 15.1&nbsp;



 <A HREF="except.html#except.throw">except.throw</A> paragraph 3 from</P>

<BLOCKQUOTE>

A <I>throw-expression</I> initializes a temporary object, the type of
which is determined...

</BLOCKQUOTE>

<P>to</P>

<BLOCKQUOTE>

A <I>throw-expression</I> initializes a temporary object, called the
<I>exception object</I>, the type of which is determined...

</BLOCKQUOTE>
</LI>

<LI>
<P>Change 15.3&nbsp;



 <A HREF="except.html#except.handle">except.handle</A> paragraph 3 from</P>

<BLOCKQUOTE>

A <I>handler</I> is a match for a <I>throw-expression</I> with an
object of type <TT>E</TT> if...

</BLOCKQUOTE>

<P>to</P>

<BLOCKQUOTE>

A <I>handler</I> is a match for an exception object of type <TT>E</TT>
if...

</BLOCKQUOTE>
</LI>
</OL>

<BR>
<BR>
<HR>
<A NAME="25"></A>
<H4>25.
  
Exception specifications and pointers to members
</H4>
<B>Section: </B>15.4&nbsp;



 <A HREF="except.html#except.spec">except.spec</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>unknown
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>unknown<BR>





<P>15.4&nbsp;



 <A HREF="except.html#except.spec">except.spec</A>
 paragraph 3 should say what
happens when two pointers to members with
different exception specifications are assigned to each other, initialized
with one another, etc.</P>

<P>
<B>Proposed Resolution (04/99):</B>
Change the text in 15.4&nbsp;



 <A HREF="except.html#except.spec">except.spec</A>
 paragraph 3 from:</P>
<BLOCKQUOTE>Similarly, any function or pointer to function assigned to,
or initializing, a pointer to function shall only allow exceptions that
are allowed by the pointer or function being assigned to or initialized.</BLOCKQUOTE>
to:
<BLOCKQUOTE>A similar restriction applies to assignment to and initialization
of pointers to functions, pointers to member functions, and references
to functions: the target entity shall allow at least the exceptions allowed
by the source value in the assignment or initialization.</BLOCKQUOTE>
<BR>
<BR>
<HR>
<A NAME="126"></A>
<H4>126.
  
Exception specifications and <TT>const</TT>
</H4>
<B>Section: </B>15.4&nbsp;



 <A HREF="except.html#except.spec">except.spec</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Martin von Loewis
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>8 June 1999<BR>



<P>The standard is inconsistent about constness inside exception
specifications.</P>

<PRE>
    struct X {};
    struct Y:X {};

    const Y bar() {return Y();}

    void foo()throw(const X)
    {
      throw bar();
    }
</PRE>

It is unclear whether calling <TT>foo</TT> will result in a call
to <TT>std::unexpected</TT>.  According to
15.4&nbsp;



 <A HREF="except.html#except.spec">except.spec</A>
 paragraph 7,
only two cases are treated
specially with regard to inheritance: If "class X" appears in the
<I>type-id-list</I>, or if "class X*" appears in the
<I>type-id-list</I>. Neither is
the case here, so <TT>foo</TT> only allows exceptions of the same type
(<TT>const X</TT>). As a result, <TT>std::unexpected</TT> should be called.

<P>On the other hand, the intent of exception specification appears to
allow an implementation of this example as</P>

<PRE>
    void foo()
    try{
      throw bar();
    }catch(const X){
      throw;
    }catch(...){
      std::unexpected();
    }
</PRE>

According to
15.3&nbsp;



 <A HREF="except.html#except.handle">except.handle</A>
,
this replacement code would catch the exception, so
<TT>std::unexpected</TT> would not be called.

<P>Suggested resolution: Change
15.4&nbsp;



 <A HREF="except.html#except.spec">except.spec</A>
 paragraph 7 to read</P>

<BLOCKQUOTE>
A function is said to <I>allow</I> all exception objects of all
types <TT>E</TT> for which one of the types <TT>T</TT>
in the <I>type-id-list</I> would be a handler, according to
15.3&nbsp;



 <A HREF="except.html#except.handle">except.handle</A>
.
</BLOCKQUOTE>

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>Replace 15.4&nbsp;



 <A HREF="except.html#except.spec">except.spec</A> paragraph 7 with the
following:</P>

<BLOCKQUOTE>

A function is said to <I>allow</I> an exception of type <TT>E</TT> if
its <I>exception-specification</I> contains a type <TT>T</TT> for
which a handler of type <TT>T</TT> would be a match (15.3&nbsp;



 <A HREF="except.html#except.handle">except.handle</A>) for an exception of type <TT>E</TT>.

</BLOCKQUOTE>
<BR>
<BR>
<HR>
<A NAME="145"></A>
<H4>145.
  
Deprecation of prefix <TT>++</TT>
</H4>
<B>Section: </B>D.1&nbsp;



 <A HREF="future.html#depr.post.incr">depr.post.incr</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>Mike Miller
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>23 Jul 1999<BR>



<P>D.1&nbsp;



 <A HREF="future.html#depr.post.incr">depr.post.incr</A>

indicates that use of the postfix <TT>++</TT> with a <TT>bool</TT>
operand is
deprecated.
Annex D&nbsp;



 <A HREF="future.html#depr">depr</A>

says nothing about prefix <TT>++</TT>.  However, this
use of prefix <TT>++</TT> is also deprecated, according to
5.3.2&nbsp;



 <A HREF="expr.html#expr.pre.incr">expr.pre.incr</A>
 paragraph 1.
Presumably D.1&nbsp;



 <A HREF="future.html#depr.post.incr">depr.post.incr</A>

should be expanded to cover prefix <TT>++</TT>, or another
section should be added to Annex
D&nbsp;



 <A HREF="future.html#depr">depr</A>.</P>

<P>
<B>Proposed resolution (10/00):</B>
</P>

<P>Change the entire section
D.1&nbsp;



 <A HREF="future.html#depr.post.incr">depr.post.incr</A>, including its heading, to read as
follows:</P>

<BLOCKQUOTE>

<TABLE CELLSPACING="0" CELLPADDING="0" FRAME="VOID" RULES="NONE" WIDTH="85%">
 <TR>
  <TD>
   <B>D.1 Increment operator with <TT>bool</TT> operand</B>
  </TD>
  <TD ALIGN="RIGHT">
   <B>[depr.incr.bool]</B>
  </TD>
 </TR>
</TABLE>

<P>The use of an operand of type <TT>bool</TT> with the <TT>++</TT>
operator is deprecated (see 5.3.2&nbsp;



 <A HREF="expr.html#expr.pre.incr">expr.pre.incr</A> and
5.2.6&nbsp;



 <A HREF="expr.html#expr.post.incr">expr.post.incr</A>).</P>

</BLOCKQUOTE>
<BR>
<BR>
<HR>
<A NAME="131"></A>
<H4>131.
  
Typo in Lao characters
</H4>
<B>Section: </B>E&nbsp;



 <A HREF="extendid.html#extendid">extendid</A>
 &nbsp;&nbsp;&nbsp;

 <B>Status: </B>TC1
 &nbsp;&nbsp;&nbsp;

 <B>Submitter: </B>John Spicer
 &nbsp;&nbsp;&nbsp;

 <B>Date: </B>23 June 1999<BR>





<P>The Lao character 0e0d should be 0e8d.  0e0d is both out of order
and already used in the Thai characters.</P>

<P>
<B>Proposed resolution (10/99):</B> As suggested.</P>
<BR>
<BR>
<BR>
<BR>
</BODY>
</HTML>
