______________________________________________________________________ 3 Basic concepts [basic] ______________________________________________________________________ 1 [Note: this clause presents the basic concepts of the C++ language. It explains the difference between an object and a name and how they relate to the notion of an lvalue. It introduces the concepts of a declaration and a definition and presents C++'s notion of type, scope, linkage, and storage duration. The mechanisms for starting and termi nating a program are discussed. Finally, this clause presents the fundamental types of the language and lists the ways of constructing compound types from these. 2 This clause does not cover concepts that affect only a single part of the language. Such concepts are discussed in the relevant clauses. --end note] 3 An entity is a value, object, subobject, base class subobject, array element, variable, function, set of functions, instance of a function, enumerator, type, class member, template, or namespace. 4 A name is a use of an identifier (_lex.name_) that denotes an entity or label (_stmt.goto_, _stmt.label_). +------- BEGIN BOX 1 -------+ We need to specifically define ``variable''. The preceding sentences say that it is an ``entity'' that has a name. Probably a variable is ``a declared object that has a name''. +------- END BOX 1 -------+ 5 Every name that denotes an entity is introduced by a declaration. Every name that denotes a label is introduced either by a goto state ment (_stmt.goto_) or a labeled-statement (_stmt.label_). 6 Some names denote types, classes, enumerations, or templates. In gen eral, it is necessary to determine whether or not a name denotes one of these entities before parsing the program that contains it. The process that determines this is called name lookup (_basic.lookup_). 7 Two names are the same if --they are identifiers composed of the same character sequence; or --they are the names of overloaded operator functions formed with the same operator; or --they are the names of user-defined conversion functions formed with the same type. 8 An identifier used in more than one translation unit can potentially refer to the same entity in these translation units depending on the linkage (_basic.link_) specified in the translation units. 3.1 Declarations and definitions [basic.def] 1 A declaration (_dcl.dcl_) introduces one or more names into a program and gives each name a meaning. 2 A declaration is a definition unless it declares a function without specifying the function's body (_dcl.fct.def_), it contains the extern specifier (_dcl.stc_) and neither an initializer nor a function-body, it declares a static data member in a class declaration (_class.static_), it is a class name declaration (_class.name_), or it is a typedef declaration (_dcl.typedef_), a using declara tion(_namespace.udecl_), or a using directive(_namespace.udir_). 3 [Example: all but one of the following are definitions: int a; // defines a extern const int c = 1; // defines c int f(int x) { return x+a; } // defines f struct S { int a; int b; }; // defines S struct X { // defines X int x; // defines nonstatic data member x static int y; // declares static data member y X(): x(0) { } // defines a constructor of X }; int X::y = 1; // defines X::y enum { up, down }; // defines up and down namespace N { int d; } // defines N and N::d namespace N1 = N; // defines N1 X anX; // defines anX whereas these are just declarations: extern int a; // declares a extern const int c; // declares c int f(int); // declares f struct S; // declares S typedef int Int; // declares Int extern X anotherX; // declares anotherX using N::d; // declares N::d --end example] 4 [Note: in some circumstances, C++ implementations implicitly define the default constructor (_class.ctor_), copy constructor (_class.copy_), assignment operator (_class.copy_), or destructor (_class.dtor_) member functions. [Example: given struct C { string s; // string is the standard library class (_lib.string_) }; int main() { C a; C b = a; b = a; } the implementation will implicitly define functions to make the defi nition of C equivalent to struct C { string s; C(): s() { } C(const C& x): s(x.s) { } C& operator=(const C& x) { s = x.s; return *this; } ~C() { } }; --end example] --end note] 5 [Note: a class name can also be implicitly declared by an elaborated- type-specifier (_basic.scope.pdecl_). ] 3.2 One definition rule [basic.def.odr] 1 No translation unit shall contain more than one definition of any variable, function, class type, enumeration type or template. 2 A function is used if it is called, its address is taken, it is used to form a pointer to member, or it is a virtual member function that is not pure (_class.abstract_). Every program shall contain at least one definition of every function that is used in that program. That definition can appear explicitly in the program, it can be found in the standard or a user-defined library, or (when appropriate) it is implicitly defined (see _class.ctor_, _class.dtor_ and _class.copy_). If a non-virtual function is not defined, a diagnostic is required only if an attempt is actually made to call that function. If a vir tual function is not defined and it is neither called nor used to form a pointer to member, no diagnostic is required. +------- BEGIN BOX 2 -------+ This says nothing about user-defined libraries. Probably it shouldn't, but perhaps it should be more explicit that it isn't dis cussing it. +------- END BOX 2 -------+ 3 A non-local variable with static storage duration shall have exactly one definition in a program unless the variable either has a builtin type or is an aggregate and unless it is either unused or used only as the operand of the sizeof operator. +------- BEGIN BOX 3 -------+ This is still uncertain. +------- END BOX 3 -------+ 4 Exactly one definition of a class is required in a translation unit if the class is used other than in the formation of a pointer or refer ence type. +------- BEGIN BOX 4 -------+ This is not quite right, because it is possible to declare a function that has an undefined class type as its return type, that has argu ments of undefined class type. +------- END BOX 4 -------+ +------- BEGIN BOX 5 -------+ There might be other situations that do not require a class to be defined: extern declarations (i.e. "extern X x;"), declaration of static members, others??? +------- END BOX 5 -------+ 5 [Example: the following complete translation unit is well-formed, even though it never defines X: struct X; // declare X as a struct type struct X* x1; // use X in pointer formation X* x2; // use X in pointer formation --end example] 6 There can be more than one definition of a class type (_class_), enu meration type (_dcl.enum_), inline function with external linkage (_dcl.fct.spec_), class template (_temp_), non-static function tem plate (_temp.fct_), static data member of a class template (_temp.static_), member function template (_temp.mem.func_), or tem plate specialization for which some template parameters are not speci fied (_temp.spec_, _temp.class.spec_) in a program provided that each definition appears in a different translation unit, and provided the definitions satisfy the following requirements. Given such an entity named D defined in more than one translation unit, then --each definition of D shall consist of the same sequence of tokens; and --in each definition of D, corresponding names, looked up according to _basic.lookup_, shall refer to an entity defined within the defini tion of D, or shall refer to the same entity, after overload resolu tion (_over.match_) and after matching of partial template special ization (_temp.over_), except that a name can refer to a const object with internal or no linkage if the object has the same inte gral or enumeration type in all definitions of D, and the object is initialized with a constant expression (_expr.const_), and the value (but not the address) of the object is used, and the object has the same value in all definitions of D; and --in each definition of D, the overloaded operators referred to, the implicit calls to conversion operators, constructors, operator new functions and operator delete functions, shall refer to the same function, or to a function defined within the definition of D; and --in each definition of D, a default argument used by an (implicit or explicit) function call is treated as if its token sequence were present in the definition of D; that is, the default argument is subject to three requirements described above (and, if the default argument has sub-expressions with default arguments, this require ment applies recursively).1) --if D is a class with an implicitly-declared constructor (_class.ctor_), it is as if the constructor was implicitly defined in every translation unit where it is used, and the implicit defini tion in every translation unit shall call the same constructor for a base class or a class member of D. [Example: // translation unit 1: struct X { X(int); X(int, int); }; X::X(int = 0) { } class D: public X { }; D d2; // X(int) called by D() // translation unit 2: struct X { X(int); X(int, int); }; X::X(int = 0, int = 0) { } // X(int, int) called by D(); // D()'s implicit definition // violates the ODR --end example] If D is a template, and is defined in more than one translation unit, then the last four requirements from the list above shall apply to names from the template's enclosing scope used in the template definition (_temp.encl_), and also to dependent names at the point of instantiation (_temp.dep_). If the defini tions of D satisfy all these requirements, then the program shall behave as if there were a single definition of D. If the defini tions of D do not satisfy these requirements, then the behavior is undefined. _________________________ 1) _dcl.fct.default_ describes how default argument names are looked up. 3.3 Declarative regions and scopes [basic.scope] 1 Every name is introduced in some contiguous portion of program text called a declarative region, which is the largest part of the program in which that name can possibly be valid. In general, each particular name is valid only within some possibly discontiguous portion of pro gram text called its scope. To determine the scope of a declaration, it is sometimes convenient to refer to the potential scope of a decla ration. The scope of a declaration is the same as its potential scope unless the potential scope contains another declaration of the same name. In that case, the potential scope of the declaration in the inner (contained) declarative region is excluded from the scope of the declaration in the outer (containing) declarative region. 2 [Example: in int j = 24; int main() { int i = j, j; j = 42; } the identifier j is declared twice as a name (and used twice). The declarative region of the first j includes the entire example. The potential scope of the first j begins immediately after that j and extends to the end of the program, but its (actual) scope excludes the text between the , and the }. The declarative region of the second declaration of j (the j immediately before the semicolon) includes all the text between { and }, but its potential scope excludes the decla ration of i. The scope of the second declaration of j is the same as its potential scope. ] 3 [Note: The name look up rules are summarized in _basic.lookup_. ] 3.3.1 Point of declaration [basic.scope.pdecl] 1 The point of declaration for a name is immediately after its complete declarator (_dcl.decl_) and before its initializer (if any), except as noted below. [Example: int x = 12; { int x = x; } Here the second x is initialized with its own (unspecified) value. ] 2 A nonlocal name remains visible up to the point of declaration of the local name that hides it. [Example: const int i = 2; { int i[i]; } declares a local array of two integers. ] 3 The point of declaration for an enumerator is immediately after its enumerator-definition. [Example: const int x = 12; { enum { x = x }; } Here, the enumerator x is initialized with the value of the constant x, namely 12. ] 4 The point of declaration of a class first declared in an elaborated- type-specifier is as follows: --if the elaborated-type-specifier has the form: class-key identifier ; the elaborated-type-specifier declares the identifier to be a class- name in the scope that contains the declaration, otherwise --if the elaborated-type-specifier has the form class-key identifier ... the identifier is declared as a class-name in the smallest non- class, non-function prototype scope that contains the declaration. [Note: this also applies to friend declarations of the form: friend class-key identifier ; where the identifier refers to a class that has not been previously declared. ] [Note: any other form of elaborated-type-specifier must refer to an already declared class-name or enum-name; see _basic.lookup.elab_. ] 5 A function declared as a friend and not previously declared, is intro duced in the smallest enclosing non-class, non-function prototype scope that contains the friend declaration. 6 [Note: For point of instantiation of a template, see _temp.inst_. ] 3.3.2 Local scope [basic.scope.local] 1 A name declared in a block (_stmt.block_) is local to that block. Its scope begins at its point of declaration (_basic.scope.pdecl_) and ends at the end of its declarative region. 2 A function parameter name in a function definition (_dcl.fct.def_) is a local name in the scope of the outermost block of the function and shall not be redeclared in that scope. 3 The name in a catch exception-declaration is local to the handler and shall not be redeclared in the outermost block of the handler. 4 Names declared in the for-init-statement, and in the condition of if, while, for, and switch statements are local to the if, while, for, or switch statement (including the controlled statement), and shall not be redeclared in a subsequent condition of that statement nor in the outermost block (or, for the if statement, any of the outermost blocks) of the controlled statement; see _stmt.select_. 3.3.3 Function prototype scope [basic.scope.proto] 1 In a function declaration, or in any function declarator except the declarator of a function definition (_dcl.fct.def_), names of parame ters (if supplied) have function prototype scope, which terminates at the end of the nearest enclosing function declarator. 3.3.4 Function scope 1 Labels (_stmt.label_) can be used anywhere in the function in which they are declared. Only labels have function scope. 3.3.5 Namespace scope [basic.scope.namespace] 1 The declarative region of a namespace-definition is its namespace- body. The potential scope denoted by an original-namespace-name is the concatenation of the declarative regions established by each of the namespace-definitions in the same declarative region with that original-namespace-name. Entities declared in a namespace-body are said to be members of the namespace, and names introduced by these declarations into the declarative region of the namespace are said to be member names of the namespace. A namespace member name has names pace scope. Its potential scope includes its namespace from the name's point of declaration (_basic.scope.pdecl_) onwards, as well as the potential scope of any using directive (_namespace.udir_) that nominates its namespace. [Example: namespace N { int i; int g(int a) { return a; } int k(); void q(); } namespace { int l=1; } // the potential scope of l is from its point of declaration // to the end of the translation unit namespace N { int g(char a) // overloads N::g(int) { return l+a; // l is from unnamed namespace } int i; // error: duplicate definition int k(); // ok: duplicate function declaration int k() // ok: definition of N::k() { return g(i); // calls N::g(int) } int q(); // error: different return type } --end example] 2 A namespace member can also be used after the :: scope resolution operator (_expr.prim_) applied to the name of its namespace; see _namespace.qual_. 3 A name declared outside all named or unnamed namespaces (_basic.namespace_), blocks (_stmt.block_) and classes (_class_) has global namespace scope (also called global scope). The potential scope of such a name begins at its point of declaration (_basic.scope.pdecl_) and ends at the end of the translation unit that is its declarative region. Names declared in the global namespace scope are said to be global. 3.3.6 Class scope [basic.scope.class] 1 The following rules describe the scope of names declared in classes. 1)The scope of a name declared in a class consists not only of the declarative region following the name's declarator, but also of all function bodies, default arguments, and constructor ctor- initializers in that class (including such things in nested classes). 2)A name N used in a class S shall refer to the same declaration when re-evaluated in its context and in the completed scope of S. 3)If reordering member declarations in a class yields an alternate valid program under (1) and (2), the program's behavior is ill- formed, no diagnostic required. 4)A declaration in a nested declarative region hides a declaration whose declarative region contains the nested declarative region. 5)A declaration within a member function hides a declaration whose scope extends to or past the end of the member function's class. 6)The scope of a declaration that extends to or past the end of a class definition also extends to the regions defined by its member definitions, even if defined lexically outside the class (this includes static data member definitions, nested class definitions and member function definitions (that is, the parameter- declaration-clause including default arguments (_dcl.fct.default_), the member function body and, for constructor functions (_class.ctor_), the ctor-initializer (_class.base.init_)). [Example: typedef int c; enum { i = 1 }; class X { char v[i]; // error: 'i' refers to ::i // but when reevaluated is X::i int f() { return sizeof(c); } // okay: X::c char c; enum { i = 2 }; }; typedef char* T; struct Y { T a; // error: 'T' refers to ::T // but when reevaluated is Y::T typedef long T; T b; }; struct Z { int f(const R); // error: 'R' is parameter name // but swapping the two declarations // changes it to a type typedef int R; }; --end example] 2 The name of a class member shall only be used as follows: --in the scope of its class (as described above) or a class derived (_class.derived_) from its class, --after the . operator applied to an expression of the type of its class (_expr.ref_) or a class derived from its class, --after the -> operator applied to a pointer to an object of its class (_expr.ref_) or a class derived from its class, --after the :: scope resolution operator (_expr.prim_) applied to the name of its class or a class derived from its class, --or after a using declaration (_namespace.udecl_). 3 [Note: The scope of names introduced by friend declarations is described in _basic.scope.pdecl_. ] 3.3.7 Name hiding [basic.scope.hiding] 1 A name can be hidden by an explicit declaration of that same name in a nested declarative region or derived class (_class.member.lookup_). 2 A class name (_class.name_) or enumeration name (_dcl.enum_) can be hidden by the name of an object, function, or enumerator declared in the same scope. If a class or enumeration name and an object, func tion, or enumerator are declared in the same scope (in any order) with the same name, the class or enumeration name is hidden wherever the object, function, or enumerator name is visible. 3 In a member function definition, the declaration of a local name hides the declaration of a member of the class with the same name; see _basic.scope.class_. The declaration of a member in a derived class (_class.derived_) hides the declaration of a member of a base class of the same name; see _class.member.lookup_. 4 If a name is in scope and is not hidden it is said to be visible. 3.4 Name look up [basic.lookup] 1 The name look up rules apply uniformly to all names (including type def-names (_dcl.typedef_), namespace-names (_basic.namespace_) and class-names (_class.name_)) wherever the grammar allows such names in the context discussed by a particular rule. Name look up associates the use of a name with a declaration (_basic.def_) of that name. Name look up shall find an unambiguous declaration for the name (see _class.member.lookup_). Name look up may associate more than one dec laration with a name if it finds the name to be a function name; the declarations are said to form a set of overloaded functions (_over.load_). Overload resolution (_over.match_) takes place after name look up has succeeded. The access rules (_class.access_) are considered only once name look up and function overload resolution (if applicable) have succeeded. Only after name look up, function over load resolution (if applicable) and access checking have succeeded are the attributes introduced by the name's declaration used further in expression processing (_expr_). 2 _basic.link_ discusses linkage issues. The notions of scope, point of declaration and name hiding are discussed in _basic.scope_. 3.4.1 Unqualified name look up [basic.lookup.unqual] 1 In all the cases listed in this subclause, the scopes are searched for a declaration in the order listed in each of the respective category; name look up ends as soon as a declaration is found for the name. If no declaration is found, the program is ill-formed. 2 The declarations from the namespace nominated by a using-directive become visible in a namespace enclosing the using-directive; see _namespace.udir_. For the purpose of the unqualified name look up rules described in this subclause, the declarations from the namespace nominated by the using-directive are considered members of the enclos ing namespace. 3 A name used in global scope, outside of any function, class or user- declared namespace, shall be declared before its used in global scope. 4 A name used in a named namespace outside of the definition of any function or class shall be declared before its use in that namespace or before its use in a namespace enclosing its namespace. 5 A name used in the definition of a function that is a member of names pace N (where, only for the purpose of exposition, N could represent the global scope) shall be declared before its use in the block in which it is used or in one of its enclosing blocks (_stmt.block_) or, shall be declared before its use in namespace N or, if N is a nested namespace, shall be declared before its use in one of N's enclosing named namespaces, or shall be declared before its use in a namespace enclosing the definition of the function using the name. [Example: namespace A { namespace N { void f(); } } void A::N::f() { i = 5; // The following scopes are searched for a declaration of i: // 1) function scope of A::N::f, before the use of i // 2) scope of namespace N // 3) scope of namespace A // 4) global scope, before the definition of A::N::f } --end example] 6 A name used in the definition of a class X outside of any inline mem ber function or nested class definition shall be declared in one of the following ways: --before its use in class X or be a member of a base class of X (_class.member.lookup_), or --if X is a nested class of class Y (_class.nest_), before the defini tion of class X in Y, or shall be a member of a base class of Y (this look up applies recursively for all of Y's enclosing classes), or --if X is a local class (_class.local_), before the definition of class X in a block enclosing the definition of class X, or --if X is a member of namespace N, before the definition of class X in namespace N or in one of N's enclosing named namespaces, or --before the definition of class X, in a namespace enclosing the defi nition of class X. [Note: _basic.scope.class_ further describes the restrictions on the use of names in a class definition. _class.nest_ further describes the restrictions on the use of names in nested class definitions. _class.local_ further describes the restrictions on the use of names in local class definitions. ] [Example: namespace M { class B { }; } namespace N { class Y : public M::B { class X { int a[i]; }; }; } // The following scopes are searched for a declaration of i: // 1) scope of class N::Y::X, before the use of i // 2) scope of class N::Y, before the definition of N::Y::X // 3) scope of N::Y's base class M::B // 4) scope of namespace N, before the definition of N::Y // 5) global scope, before the definition of N --end example] 7 A name used in a function that is a member function (_class.mfct_) of class X shall be declared in one of the following ways: --before its use in the block in which it is used or in an enclosing block (_stmt.block_), or --shall be a member of class X or be a member of a base class of X (_class.member.lookup_), or --if X is a nested class of class Y (_class.nest_), shall be a member of Y, or shall be a member of a base class of Y (this look up applies recursively for all of Y's enclosing classes), or --if X is a local class (_class.local_), before the definition of class X in a block enclosing the definition of class X, or --if X is a member of namespace N, before the member function defini tion, in namespace N or in one of N's enclosing named namespaces, or --before the member function definition, in a namespace enclosing the member function definition. [Note: _class.mfct_ and _class.static_ further describe the restric tions on the use of names in member function definitions. _class.nest_ further describes the restrictions on the use of names in the scope of nested classes. _class.local_ further describes the restrictions on the use of names in local class definitions. ] [Exam ple: class B { }; namespace M { namespace N { class X : public B { void f(); }; } } void M::N::X::f() { i = 16; } // The following scopes are searched for a declaration of i: // 1) function scope of M::N::X::f, before the use of i // 2) scope of class M::N::X // 3) scope of M::N::X's base class B // 4) scope of namespace M::N // 5) scope of namespace M // 5) global scope, before the definition of M::N::X::f --end example] 8 Name look up for a name used in the definition of a friend function (_class.friend_) defined inline in the class granting friendship shall proceed as described for look up in member function definitions. If the friend function is not defined in the class granting friendship, name look up in the friend function definition shall proceed as described for look up in namespace member function definitions. 9 A name used in a function parameter-declaration-clause as a default argument (_dcl.fct.default_) or used in the expression of a mem- initializer (_class.base.init_) is looked up as if the name were used in the outermost block of the function definition. In particular, the function parameter names are visible for name look up in default argu ments and in mem-initializers. [Note: _dcl.fct.default_ further describes the restrictions on the use of names in default arguments. _class.base.init_ further describes the restrictions on the use of names in a ctor-initializer. ] 10A name used in the definition of a static member of class X (_class.static.data_) (after the qualified-id of the static member) is looked up as if the name was used in a member function of X. [Note: _class.static.data_ further describes the restrictions on the use of names in the definition of a static data member. ] +------- BEGIN BOX 6 -------+ This subclause should probably say something about name look up in template definitions. +------- END BOX 6 -------+ 3.4.2 Qualified name look up [basic.lookup.qual] 1 The name of a class or namespace member can be referred to after the :: scope resolution operator (_expr.prim_) applied to a nested-name- specifier that nominates its class or namespace. During the look up for a name preceeding the :: scope resolution operator, only class names and namespace names are considered. A class-name hidden by a name that is not a type name or namespace-name is still found and used. The class-name shall have been previously declared by a class declaration (_class_). A namespace-name hidden by a name that is not a type name is still found and used. The namespace-name shall have been previously defined either by a named-namespace-definition or a namespace-alias-definition (_namespace.def_). [Example: class A { public: static int n; }; int main() { int A; A::n = 42; // OK A b; // ill-formed: A does not name a type } --end example] 2 [Note: Multiply qualified names, such as N1::N2::N3::n, can be used to refer to members of nested classes (_class.nest_) or members of nested namespaces. ] 3 In a declaration in which the declarator-id is a qualified-id, names used before the qualified-id being declared are looked up in the defining namespace scope; names following the qualified-id are looked up in the scope of the member's class or namespace. [Example: class X { }; class C { class X { }; const int number = 50; static X arr[number]; }; X C::arr number ; // equivalent to: X C::arr[C::number]; // not to: C::X C::arr[C::number]; --end example] 4 A name prefixed by the unary scope operator :: (_expr.prim_) is looked up in global scope. The use of :: allows a global name to be referred to even if its identifier has been hidden (_basic.scope.hiding_). The name shall be of global namespace scope or shall be a name whose dec laration is visible in global scope because of a using directive (see _namespace.udir_). 3.4.2.1 Class members [class.qual] 1 If the nested-name-specifier of a qualified-id nominates a class, the name specified after the nested-name-specifier is looked up in the scope of the class. The name shall represent a member of that class or a member of one of its base classes (_class.derived_). [Note: _class.member.lookup_ describes how name look up proceeds in class scope. ] 2 A class member name hidden by a name in a nested declarative region or by the name of a derived class member can still be found if qualified by the name of its class followed by the :: operator. 3.4.2.2 Namespace members [namespace.qual] 1 If the nested-name-specifier of a qualified-id nominates a namespace, the name specified after the nested-name-specifier is looked up in the scope of the namespace. 2 Given X::m, where X is a namespace, if m is declared directly in X, let S be the set of all such declarations of m. Else if there are no using-directives in X, S is the empty set. Else let S be the union of all sets of declarations of m found in the namespaces designated by the using-directives in X. If m is declared directly in these names paces, let S be the set of all such declarations of m. Else if these namespaces do not contain any using-directives, S is the empty set. Else, this search is applied recursively to the namespaces designated by the using-directives in these namespaces. No namespace is searched more than once in the lookup of a name. If S is the empty set the program is ill-formed, otherwise S is the required set of declarations of m. If S has exactly one member then X::m refers to that member. Otherwise if the use of m is not one that allows a unique declaration to be chosen from S, the program is ill-formed. [Note: the choice could be made by overload resolution (_over.match_) or resolution between class names and non-class names (_class.name_). For example: int x; namespace Y { void f(float); void h(int); } namespace Z { void h(float); } namespace A { using namespace Y; void f(int); void g(int); int i; } namespace B { using namespace Z; void f(char); int i; } namespace AB { using namespace A; using namespace B; void g(); } void h() { AB::g(); // g is declared directly in AB, // therefore S is { AB::g() } and AB::g() is chosen AB::f(1); // f is not declared directly in AB so the rules are // applied recursively to A and B; // namespace Y is not searched and Y::f(float) // is not considered; // S is { A::f(int), B::f(char) } and overload // resolution chooses A::f(int) AB::f('c'); // as above but resolution chooses B::f(char) AB::x++; // x is not declared directly in AB, and // is not declared in A or B, so the rules are // applied recursively to Y and Z, // S is { } so the program is ill-formed AB::i++; // i is not declared directly in AB so the rules are // applied recursively to A and B, // S is { A::i, B::i } so the use is ambiguous // and the program is ill-formed AB::h(16.8); // h is not declared directly in AB and // not declared directly in A or B so the rules are // applied recursively to Y and Z, // S is { Y::h(int), Z::h(float) } and overload // resolution chooses Z::h(float) } 3 The same declaration found more than once is not an ambiguity (because it is still a unique declaration). For example: namespace A { int a; } namespace B { using namespace A; } namespace C { using namespace A; } namespace BC { using namespace B; using namespace C; } void f() { BC::a++; // ok: S is { A::a, A::a } } namespace D { using A::a; } namespace BD { using namespace B; using namespace D; } void g() { BD::a++; // ok: S is { A::a, A::a } } 4 Since each referenced namespace is searched at most once, the follow ing is well-defined: namespace B { int b; } namespace A { using namespace B; int a; } namespace B { using namespace A; } void f() { A::a++; // ok: a declared directly in A, S is { A::a } B::a++; // ok: both A and B searched (once), S is { A::a } A::b++; // ok: both A and B searched (once), S is { B::b } B::b++; // ok: b declared directly in B, S is { B::b } } --end note] 5 During the look up of a qualified namespace member name, if the look up finds more than one declaration of the member, and if one declara tion introduces a class name or enumeration name and the other decla rations either introduce the same object, the same enumerator or a set of functions, the non-type name hides the class or enumeration name if and only if the declarations are from the same namespace; otherwise (the declarations are from different namespaces), the program is ill- formed. [Example: namespace A { struct x { }; int x; int y; } namespace B { struct y {}; } namespace C { using namespace A; using namespace B; int i = C::x; // ok, A::x (of type 'int') int j = C::y; // ambiguous, A::y or B::y } --end example] +------- BEGIN BOX 7 -------+ Change: The paragraph above is the result of discussions from the core reflector; see core-6070. +------- END BOX 7 -------+ 6 In a declaration for a namespace member in which the declarator-id is a qualified-id, given that the qualified-id for the namespace member has the form nested-name-specifier unqualified-id the unqualified-id shall name a member of the namespace designated by the nested-name-specifier. [Example: namespace A { namespace B { void f1(int); } using namespace B; } void A::f1(T){} // ill-formed, f1 is not a member of A --end example] However, in such namespace member declarations, the nested-name-specifier may rely on using-directives to implicitly pro vide the initial part of the nested-name-specifier. [Example: namespace A { namespace B { void f1(int); } } namespace C { namespace D { void f1(int); } } using namespace A; using namespace C::D; void B::f1(int){} // okay, defines A::B::f1(int) void f1(int){} // okay, defines C::D::f1(int) --end example] +------- BEGIN BOX 8 -------+ Change: The paragraph above is the result of discussions from the core reflector; see core-6107. +------- END BOX 8 -------+ 3.4.3 Elaborated type specifiers [basic.lookup.elab] 1 An elaborated-type-specifier may be used to refer to a previously declared class-name or enum-name even though the name has been hidden by an intervening object, function, or enumerator declaration (_basic.scope.hiding_). The class-name or enum-name in the elabo rated-type-specifier may either be a single identifer or be a quali fied-id. 2 If the name in the elaborated-type-specifier is a single identifer, and unless the elaborated-type-specifier has the following form: class-key identifier ; the identifier is looked up according to _basic.lookup.unqual_ but ignoring any objects, functions or enumerators that have been declared. If this name look up finds a typedef_name, the elaborated- type-specifier is ill-formed. If the elaborated-type-specifier refers to an enum-name and this look up does not find a previously declared enum-name, the elaborated-type-specifier is ill-formed. If the elabo rated-type-specifier refers to an class-name and this look up does not find a previously declared class-name, or if the elaborated-type- specifier has the form: class-key identifier ; the elaborated-type-specifier is a declaration that introduces the class-name as described in _basic.scope.pdecl_. 3 If the elaborated-type-specifier is a qualified-id, the name is looked up according its qualifications, as described in _basic.lookup.qual_, but ignoring any objects, functions or enumerators that have been declared. If this name look up finds a typedef_name, the elaborated- type-specifier is ill-formed. If this name look up does not find a previously declared class-name or enum-name, the elaborated-type- specifier is ill-formed. [Example: struct Node { struct Node* Next; // ok: Refers to Node at global scope struct Data* Data; // ok: Declares type Data // at global scope and member Data }; struct Data { struct Node* Node; // ok: Refers to Node at global scope friend struct ::Glob; // error: Glob is not declared // cannot introduce a qualified type friend struct Glob; // ok: Declares Glob in global scope /* ... */ }; struct Base { struct Data; // ok: Declares nested Data struct ::Data* thatData; // ok: Refers to ::Data struct Base::Data* thisData; // ok: Refers to nested Data friend class ::Data; // ok: global Data is a friend friend class Data; // ok: nested Data is a friend struct Data { /* ... */ }; // Defines nested Data struct Data; // ok: Redeclares nested Data }; struct Data; // ok: Redeclares Data at global scope struct ::Data; // error: cannot introduce a qualified type struct Base::Data; // error: cannot introduce a qualified type struct Base::Datum; // error: Datum undefined struct Base::Data* pBase; // ok: refers to nested Data --end example] 3.4.4 Class member access [basic.lookup.classref] 1 A name specified after the . operator or -> operator of a class member access is looked up as specified in _expr.ref_. +------- BEGIN BOX 9 -------+ This subclause needs work. _expr.ref_ is not really clear in describ ing how names after the . operator and -> operator are looked up. See core issue 452a. +------- END BOX 9 -------+ 3.5 Program and linkage [basic.link] 1 A program consists of one or more translation units (_lex_) linked together. A translation unit consists of a sequence of declarations. translation unit: declaration-seqopt 2 A name is said to have linkage when it might denote the same object, reference, function, type, template, namespace or value as a name introduced by a declaration in another scope: --When a name has external linkage, the entity it denotes can be referred to by names from scopes of other translation units or from other scopes of the same translation unit. --When a name has internal linkage, the entity it denotes can be referred to by names from other scopes of the same translation unit. --When a name has no linkage, the entity it denotes cannot be referred to by names from other scopes. 3 A name of namespace scope (_basic.scope.namespace_) has internal link age if it is the name of --a variable that is explicitly declared static or, is explicitly declared const and neither explicitly declared extern nor previously declared to have external linkage; or --a function that is explicitly declared static or, is explicitly declared inline and neither explicitly declared extern nor previ ously declared to have external linkage; or --the name of a data member of an anonymous union. 4 A name of namespace scope has external linkage if it is the name of --a variable, unless it has internal linkage; or --a function, unless it has internal linkage; or --a named class (_class_), or an unnamed class defined in a typedef declaration in which the class has the typedef name for linkage pur poses (_dcl.typedef_); or --a named enumeration (_dcl.enum_), or an unnamed enumeration defined in a typedef declaration in which the enumeration has the typedef name for linkage purposes (_dcl.typedef_); or --an enumerator belonging to an enumeration with external linkage; or --a template (_temp_); or --a namespace (_basic.namespace_), unless it is declared within an unnamed namespace. 5 In addition, a name of class scope has external linkage if the name of the class has external linkage. 6 The name of a function declared in a block scope has linkage. If the block scope function declaration matches a prior visible declaration of the same function, the function name receives the linkage of the previous declaration; otherwise, it receives external linkage. The name of an object declared by a block scope extern declaration has linkage. If the block scope declaration matches a prior visible dec laration of the same object, the name introduced by the block scope declaration receives the linkage of the previous declaration; other wise, it receives external linkage. [Example: static void f(); static int i = 0; void g() { extern void f(); // internal linkage int i; // 'i' has no linkage { extern void f(); // internal linkage extern int i; // external linkage } } --end example] 7 Names not covered by these rules have no linkage. Moreover, except as noted, a name declared in a local scope (_basic.scope.local_) has no linkage. A name with no linkage (notably, the name of a class or enu meration declared in a local scope (_basic.scope.local_)) shall not be used to declare an entity with linkage. If a declaration uses a type def name, it is the linkage of the type name to which the typedef refers that is considered. [Example: void f() { struct A { int x; }; // no linkage extern A a; // ill-formed typedef A B; extern B b; // ill-formed } --end example] This implies that names with no linkage cannot be used as template arguments (_temp.arg_). 8 Two names that are the same (_basic_) and that are declared in differ ent scopes shall denote the same object, reference, function, type, enumerator, template or namespace if --both names have external linkage or else both names have internal linkage and are declared in the same translation unit; and --both names refer to members of the same namespace or to members, not by inheritance, of the same class; and --when both names denote functions, the function types are identical for purposes of overloading; and --when both names denote function templates, the signatures (_temp.over.link_) are the same. 9 After all adjustments of types (during which typedefs (_dcl.typedef_) are replaced by their definitions), the types specified by all decla rations of a particular external name shall be identical, except that declarations for an array object can specify array types that differ by the presence or absence of a major array bound (_dcl.array_), and declarations for functions with the same name can specify different numbers and types of parameters (_dcl.fct_). A violation of this rule on type identity does not require a diagnostic. 10[Note: linkage to non-C++ declarations can be achieved using a link age-specification (_dcl.link_). ] 3.6 Start and termination [basic.start] 3.6.1 Main function [basic.start.main] 1 A program shall contain a global function called main, which is the designated start of the program. +------- BEGIN BOX 10 -------+ In C, a freestanding environment does not require main; the program invocation method is implementation-defined. Should C++? [Yes, C++ should require main - because unlike in C, this C++ standard defines the semantics of program start and termination. This was done so that freestanding environments can get the same level of definition for order of static constructors/destructors. --Neal Gafter] +------- END BOX 10 -------+ 2 This function is not predefined by the implementation, it cannot be overloaded, and its type is implementation-defined. All implementa tions shall allow both of the following definitions of main: int main() { /* ... */ } and int main(int argc, char* argv[]) { /* ... */ } In the latter form argc shall be the number of arguments passed to the program from the environment in which the program is run. If argc is nonzero these arguments shall be supplied in argv[0] through argv[argc-1] as pointers to the initial characters of null-terminated multibyte strings (NTMBSs) and argv[0] shall be the pointer to the initial character of a NTMBS that represents the name used to invoke the program or "". The value of argc shall be nonnegative. The value of argv[argc] shall be 0. [Note: It is recommended that any further (optional) parameters be added after argv. ] 3 The function main() shall not be called from within a program. The linkage (_basic.link_) of main() is implementation-defined. The address of main() shall not be taken and main() shall not be declared inline or static. The name main is not otherwise reserved. [Example: member functions, classes, and enumerations can be called main, as can entities in other namespaces. ] 4 Calling the function void exit(int); declared in <cstdlib> (_lib.support.start.term_) terminates the pro gram without leaving the current block and hence without destroying any objects with automatic storage duration (_class.dtor_). The argu ment value is returned to the program's environment as the value of the program. +------- BEGIN BOX 11 -------+ Several members of the Core editing group question this. Can we require that exit destroy automatic-duration objects? Or make it implementation-defined whether the unwinding occurs? If an imple menter's market _wants_ exit to unwind, and the implementer can pro vide the necessary stack-unwinding, why should the Standard prohibit it? For an immediate ``get me out of here'', there is always the abort function. The footnote in _lib.exit_ claims that an unwinding can be achieved by throwing an exception that is caught in main, but this assumes and requires that no handlers for ... intervene. There appears to be no way of exiting via exception that cannot be inter cepted by such handlers. +------- END BOX 11 -------+ 5 A return statement in main() has the effect of leaving the main func tion (destroying any objects with automatic storage duration) and calling exit() with the return value as the argument. If control reaches the end of main without encountering a return statement, the effect is that of executing return 0; 3.6.2 Initialization of non-local objects [basic.start.init] 1 The initialization of nonlocal objects with static storage duration (_basic.stc_) defined in a translation unit is done before the first use of any function or object defined in that translation unit. Such initializations (_dcl.init_, _class.static_, _class.ctor_, _class.expl.init_) can be done before the first statement of main() or deferred to any point in time before the first use of a function or object defined in that translation unit. The storage for objects with static storage duration is zero-initialized (_dcl.init_) before any other initialization takes place. Objects with static storage dura tion initialized with constant expressions (_expr.const_) are initial ized before any dynamic (that is, run-time) initialization takes place. The order of initialization of nonlocal objects with static storage duration defined in the same translation unit is the order in which their definition appears in this translation unit. No further order is imposed on the initialization of objects from different translation units. The initialization of local static objects is described in _stmt.dcl_. 2 If construction or destruction of a non-local static object ends in throwing an uncaught exception, the result is to call terminate() (_lib.terminate_). 3.6.3 Termination [basic.start.term] 1 Destructors (_class.dtor_) for initialized static objects are called when returning from main() and when calling exit() (_lib.support.start.term_). Destruction is done in the reverse order of initialization. The function atexit() from <cstdlib> can be used to specify a function to be called at exit. If atexit() is to be called, the implementation shall not destroy objects with static stor age duration initialized before an atexit() call until after the func tion specified in the atexit() call has been called. 2 Where a C++ implementation coexists with a C implementation, any actions specified by the C implementation to take place after the atexit() functions have been called take place after all destructors have been called. 3 Calling the function void abort(); declared in <cstdlib> terminates the program without executing destructors for objects of automatic or static storage duration and without calling the functions passed to atexit(). 3.7 Storage duration [basic.stc] 1 Storage duration is a property of an object that indicates the poten tial time extent the storage in which the object resides might last. The storage duration is determined by the construct used to create the object and is one of the following: --static storage duration --automatic storage duration --dynamic storage duration 2 Static and automatic storage durations are associated with objects introduced by declarations (_basic.def_). The dynamic storage dura tion is associated with objects created with operator new (_expr.new_). 3 The storage class specifiers static and auto are related to storage duration as described below. 4 References (_dcl.ref_) might or might not require storage; however, the storage duration categories apply to references as well. 3.7.1 Static storage duration [basic.stc.static] 1 All non-local objects have static storage duration. The storage for these objects shall last for the duration of the program. These objects are initialized and destroyed as described in _basic.start.init_ and _basic.start.term_. 2 If an object of static storage duration has initialization or a destructor with side effects, it shall not be eliminated even if it appears to be unused. 3 The keyword static can be used to declare a local variable with static storage duration; for a description of initialization and destruction of local static variables, see _stmt.dcl_. 4 The keyword static applied to a class data member in a class defini tion gives the data member static storage duration. 3.7.2 Automatic storage duration [basic.stc.auto] 1 Local objects explicitly declared auto or register or not explicitly declared static or extern have automatic storage duration. The stor age for these objects lasts until the block in which they are created exits. 2 [Note: These objects are initialized and destroyed as described _stmt.dcl_. ] 3 If a named automatic object has initialization or a destructor with side effects, it shall not be destroyed before the end of its block, nor shall it be eliminated as an optimization even if it appears to be unused. 3.7.3 Dynamic storage duration [basic.stc.dynamic] 1 Objects can be created dynamically during program execution (_intro.execution_), using new-expressions (_expr.new_), and destroyed using delete-expressions (_expr.delete_). A C++ implementation pro vides access to, and management of, dynamic storage via the global allocation functions operator new and operator new[] and the global deallocation functions operator delete and operator delete[]. 2 These functions are always implicitly declared. The library provides default definitions for them (_lib.new.delete_). A C++ program shall provide at most one definition of any of the functions ::operator new(size_t), ::operator new[](size_t), ::operator delete(void*), and/or ::operator delete[](void*). Any such function definitions replace the default versions. This replacement is global and takes effect upon program startup (_basic.start_). Allocation and/or deal location functions can also be declared and defined for any class (_class.free_). 3 Any allocation and/or deallocation functions defined in a C++ program shall conform to the semantics specified in this subclause. 3.7.3.1 Allocation functions [basic.stc.dynamic.allocation] 1 Allocation functions shall be class member functions or global func tions; a program is ill-formed if allocation functions are declared in a namespace scope other than global scope or declared static in global scope. They can be overloaded, but the return type shall always be void* and the first parameter type shall always be size_t (_expr.sizeof_), an implementation-defined integral type defined in the standard header <cstddef> (_lib.language.support_). For these functions, parameters other than the first can have associated default arguments (_dcl.fct.default_). 2 The function shall return the address of a block of available storage at least as large as the requested size. The order, contiguity, and initial value of storage allocated by successive calls to an alloca tion function is unspecified. The pointer returned is suitably aligned so that it can be assigned to a pointer of any type and then used to access such an object or an array of such objects in the stor age allocated (until the storage is explicitly deallocated by a call to a corresponding deallocation function). Each such allocation shall yield a pointer to storage (_intro.memory_) disjoint from any other currently allocated storage. The pointer returned points to the start (lowest byte address) of the allocated storage. If the size of the space requested is zero, the value returned shall be nonzero and shall not point to or within any other currently allocated storage. The results of dereferencing a pointer returned as a request for zero size are undefined.2) _________________________ 2) The intent is to have operator new() implementable by calling mal loc() or calloc(), so the rules are substantially the same. C++ dif fers from C in requiring a zero request to return a non-null pointer. 3 If an allocation function is unable to obtain an appropriate block of storage, it can invoke the currently installed new_handler3) and/or throw an exception (_except_) of class bad_alloc (_lib.bad.alloc_) or a class derived from bad_alloc. 4 If the allocation function returns the null pointer the result is implementation-defined. 3.7.3.2 Deallocation functions [basic.stc.dynamic.deallocation] 1 Deallocation functions shall be class member functions or global func tions; a program is ill-formed if deallocation functions are declared in a namespace scope other than global scope or declared static in global scope. 2 Each deallocation function shall return void and its first parameter shall be void*. For class member deallocation functions, a second parameter of type size_t may be added. If both versions are declared in the same class, the one-parameter form is the usual deallocation function and the two-parameter form is used for placement delete (_expr.new_). If the second version is declared but not the first, it is the usual deallocation function, not placement delete. 3 The value of the first parameter supplied to a deallocation function shall be zero, or refer to storage allocated by the corresponding allocation function (even if that allocation function was called with a zero argument). If the value of the first argument is zero, the call to the deallocation function has no effect. If the value of the first argument refers to a pointer already deallocated, the effect is undefined. 4 A deallocation function can free the storage referenced by the pointer given as its argument and renders the pointer invalid. The storage can be made available for further allocation. An invalid pointer con tains an unusable value: it cannot even be used in an expression. 5 If the argument is non-zero, the value of a pointer that refers to deallocated space is indeterminate. The effect of dereferencing an indeterminate pointer value is undefined.4) 3.7.4 Duration of sub-objects [basic.stc.inherit] 1 The storage duration of member subobjects, base class subobjects and array elements is that of their complete object (_intro.object_). _________________________ 3) A program-supplied allocation function can obtain the address of the currently installed new_handler (_lib.new.handler_) using the set_new_handler() function (_lib.set.new.handler_). 4) On some architectures, it causes a system-generated runtime fault. 3.8 Object Lifetime [basic.life] 1 The lifetime of an object is a runtime property of the object. The lifetime of an object of type T begins when: --storage with the proper alignment and size for type T is obtained, and --if T is a class type with a non-trivial constructor (_class.ctor_), the constructor call has completed. The lifetime of an object of type T ends when: --if T is a class type with a non-trivial destructor (_class.dtor_), the destructor call starts, or --the storage which the object occupies is reused or released. 2 [Note: the lifetime of an array object or of an object of POD types (_basic.types_) starts as soon as storage with proper size and align ment is obtained, and its lifetime ends when the storage which the array or object occupies is reused or released. _class.base.init_ describes the lifetime of base and member subobjects. ] 3 The properties ascribed to objects throughout this International Stan dard apply for a given object only during its lifetime. In particu lar, except as noted during object construction (_class.base.init_) and destruction (_class.cdtor_), before the lifetime of the object starts and after its lifetime ends the value of the storage which the object occupies is indeterminate and, for an object of non-POD class type, referring to a non-static data member, calling a non-static mem ber function or converting the object to a base class subobject results in undefined behavior. 4 [Note: the behavior of an object under construction and destruction might not be the same as the behavior of an object whose lifetime has started and not ended. _class.base.init_ and _class.cdtor_ describe the behavior of an object during the construction and destruction phases. ] 5 A program may end the lifetime of any object by reusing the storage which the object occupies or by explicitly calling the destructor for an object of a class type with a non-trivial destructor. For an object of a class type with a non-trivial destructor, the program is not required to call the destructor explicitly before the storage which the object occupies is reused or released; however, if there is no explicit call to the destructor or if a delete-expression (_expr.delete_) is not used to release the storage, the destructor is not implicitly called and any program that depends on the side effects produced by the destructor has unspecified behavior. 6 After the lifetime of an object has ended and while the storage which the object occupied still exists, any pointer to the original object can be used but only in limited ways. Such a pointer still points to valid storage and using the pointer as a pointer to the storage where the object was located, as if the pointer were of type void*, is well- defined. However, using the pointer to refer to the original object is no longer valid. In particular, such a pointer cannot be derefer enced; for a non-POD class type T, a pointer of type T* that points to the original object cannot be the operand of a static_cast (_expr.static.cast_) (except when the conversion is to void* or char*) and cannot be the operand of a dynamic_cast (_expr.dynamic.cast_); if T is a class with a non-trivial destructor, such a pointer cannot be used as the operand of a delete-expression. [Example: struct B { virtual void f(); void mutate(); virtual ~B(); }; struct D1 : B { void f(); }; struct D2 : B { void f(); }; void B::mutate() { new (this) D2; // reuses storage - ends the lifetime of '*this' f(); // undefined behavior ... = this; // ok, 'this' points to valid memory } void g() { void* p = malloc(sizeof(D1) + sizeof(D2)); B* pb = new (p) D1; pb->mutate(); &pb; // ok: pb points to valid memory void* q = pb; // ok: pb points to valid memory pb->f(); // undefined behavior, lifetime of *pb has ended } --end example] 7 If, after the lifetime of an object has ended and while the storage which the object occupied still exists, a new object is created at the storage location which the original object occupied, a pointer that pointed to the original object will automatically refer to the new object and, once the lifetime of the new object has started, can be used to manipulate the new object, if: --the storage for the new object exactly overlays the storage location which the original object occupied, and --the new object is of the same type as the original object (ignoring the top-level cv-qualifiers), and --the original object was a complete object of type T and the new object is a complete object of type T (that is, they are not base class subobjects). [Example: struct C { int i; void f(); const C& operator=( const C& ); }; const C& C::operator=( const C& other) { if ( this != &other ) { this->~C(); // lifetime of '*this' ends new (this) C(other); // new object of type C created f(); // well-defined } return *this; } C c1; C c2; c1 = c2; // well-defined c1.f(); // well-defined; c1 refers to a new object of type C --end example] 8 If a program ends the lifetime of an object of type T with static (_basic.stc.static_) or automatic (_basic.stc.auto_) storage duration and if T has a non-trivial destructor,5) the program must ensure that an object of the original type occupies that same storage location when the implicit destructor call takes place; otherwise the behavior of the program is undefined. This is true even if the block is exited with an exception. [Example: struct B { ~B(); }; void h() { B b; new (&b) T; } // undefined behavior at block exit --end example] +------- BEGIN BOX 12 -------+ const objects need special treatment. A possible solution that still needs work: 9 The storage which a const object occupies may be write-protected. Creating a new object at the storage location which a const object occupies or at the storage location which a const object used to occupy before its lifetime ended results in undefined behavior. [Example: _________________________ 5) that is, an object for which a destructor will be called implicitly -- either upon exit from the block for an object with automatic stor age duration or upon exit from the program for an object with static storage duration. struct B { ~B(); }; void h() { const B b; b.~B(); new (&b) const B; // undefined behavior } --end example] +------- END BOX 12 -------+ 3.9 Types [basic.types] 1 This clauses imposes requirements on implementations regarding the representation of types. There are two kinds of types: fundamental types and compound types. Types describe objects (_intro.object_), references (_dcl.ref_), or functions (_dcl.fct_). 2 For any object type T, the underlying bytes (_intro.memory_) of the object can be copied (using the memcpy library function (_lib.headers_)) into an array of char or unsigned char. This copy operation is well-defined, even if the object does not hold a valid value of type T. Whether or not the value of the object is later changed, if the content of the array of char or unsigned char is copied back into the object using the memcpy library function, the object shall subsequently hold its original value. [Example: #define N sizeof(T) char buf[N]; T obj; // obj initialized to its original value memcpy(buf, &obj, N); // between these two calls to memcpy, // obj might be modified memcpy(&obj, buf, N); // at this point, each subobject of obj of scalar type // holds its original value --end example] 3 For any scalar type T, if two pointers to T point to distinct T objects obj1 and obj2, if the value of obj1 is copied into obj2, using the memcpy library function, obj2 shall subsequently hold the same value as obj1. [Example: T* t1p; T* t2p; // provided that t2p points to an initialized object ... memcpy(t1p, t2p, sizeof(T)); // at this point, every subobject of scalar type in *t1p // contains the same value as the corresponding subobject in // *t2p --end example] 4 The object representation of an object of type T is the sequence of N unsigned char objects taken up by the object of type T, where N equals sizeof(T). The value representation of an object is the sequence of bits in the object representation that hold the value of type T. The bits of the value representation determine a value, which is one dis crete element of an implementation-defined set of values.6) 5 Object types have alignment requirements (_basic.fundamental_, _basic.compound_). The alignment of an object type is an implementa tion-defined integer value representing a number of bytes; an object is allocated at an address that meets the alignment requirements of its object type. 6 Arrays of unknown size and classes that have been declared but not defined are called incomplete types.7) Also, the void type is an incomplete type (and not an object type); it represents an empty set of values. No objects shall be created to have incomplete type. The term incompletely-defined object type is a synonym for incomplete type; the term completely-defined object type is a synonym for com plete type. 7 A class type (such as "class X") might be incomplete at one point in a translation unit and complete later on; the type "class X" is the same type at both points. The declared type of an array might be incom plete at one point in a translation unit and complete later on; the array types at those two points ("array of unknown bound of T" and "array of N T") are different types. However, the type of a pointer to array of unknown size, or of a type defined by a typedef declara tion to be an array of unknown size, cannot be completed. [Example: class X; // X is an incomplete type extern X* xp; // xp is a pointer to an incomplete type extern int arr[]; // the type of arr is incomplete typedef int UNKA[]; // UNKA is an incomplete type UNKA* arrp; // arrp is a pointer to an incomplete type UNKA** arrpp; void foo() { xp++; // ill-formed: X is incomplete arrp++; // ill-formed: incomplete type arrpp++; // okay: sizeof UNKA* is known } struct X { int i; }; // now X is a complete type int arr[10]; // now the type of arr is complete X x; void bar() { xp = &x; // okay; type is ``pointer to X'' arrp = &arr; // ill-formed: different types xp++; // okay: X is complete arrp++; // ill-formed: UNKA can't be completed } _________________________ 6) The intent is that the memory model of C++ is compatible with that of ISO/IEC 9899 Programming Language C. 7) The size and layout of an instance of an incomplete type is un known. --end example] 8 [Note: Clause _expr_, _stmt.stmt_, _dcl.dcl_ and _dcl.decl_ describe in which contexts incomplete types are prohibited. ] 9 Arithmetic and enumeration types (_basic.fundamental_), pointer types (_basic.compound_), and cv-qualified versions of these types (_basic.type.qualifier_) are scalar types. Scalar types, POD class types, POD union types (_class_), arrays of such types and cv- qualified versions of these types (_basic.type.qualifier_) are POD types. 10If two types T1 and T2 are the same type, then T1 and T2 are layout- compatible types. [Note: Layout-compatible enumerations are described in _dcl.enum_. Layout-compatible POD-structs and POD-unions are described in _class.mem_. ] 3.9.1 Fundamental types [basic.fundamental] 1 Objects declared as characters char) shall be large enough to store any member of the implementation's basic character set. If a charac ter from this set is stored in a character object, its value shall be equivalent to the integer code of that character. It is implementa tion-defined whether a char object can hold negative values. Charac ters can be explicitly declared unsigned or signed. Plain char, signed char, and unsigned char are three distinct types. A char, a signed char, and an unsigned char occupy the same amount of storage and have the same alignment requirements (_basic.types_); that is, they have the same object representation. For character types, all bits of the object representation participate in the value representa tion. For unsigned character types, all possible bit patterns of the value representation represent numbers. These requirements do not hold for other types. In any particular implementation, a plain char object can take on either the same values as a signed char or an unsigned char; which one is implementation-defined. 2 An enumeration comprises a set of named integer constant values, which form the basis for an integral subrange that includes those values. Each distinct enumeration constitutes a different enumerated type. Each constant has the type of its enumeration. 3 There are four signed integer types: "signed char", "short int", "int", and "long int." In this list, each type provides at least as much storage as those preceding it in the list, but the implementation can otherwise make any of them equal in storage size. Plain ints have the natural size suggested by the architecture of the execution environment8) ; the other signed integer types are provided to meet special needs. _________________________ 8) that is, large enough to contain any value in the range of INT_MIN and INT_MAX, as defined in the header <climits>. 4 For each of the signed integer types, there exists a corresponding (but different) unsigned integer type: "unsigned char", "unsigned short int", "unsigned int", and "unsigned long int," each of which occupies the same amount of storage and has the same alignment requirements (_basic.types_) as the corresponding signed integer type9) ; that is, each signed integer type has the same object repre sentation as its corresponding unsigned integer type. The range of nonnegative values of a signed integer type is a subrange of the cor responding unsigned integer type, and the value representation of the same value in each type shall be the same. 5 Unsigned integers, declared unsigned, shall obey the laws of arith metic modulo 2n where n is the number of bits in the representation of that particular size of integer.10) 6 Type wchar_t is a distinct type whose values can represent distinct codes for all members of the largest extended character set specified among the supported locales (_lib.locale_). Type wchar_t shall have the same size, signedness, and alignment requirements (_intro.memory_) as one of the other integral types, called its underlying type. 7 Values of type bool are either true or false.11) There are no signed, unsigned, short, or long bool types or values. As described below, bool values behave as integral types. Values of type bool participate in integral promotions (_conv.prom_). 8 Types bool, char, wchar_t, and the signed and unsigned integer types are collectively called integral types.12) A synonym for integral type is integer type. The representations of integral types shall define values by use of a pure binary numeration system. +------- BEGIN BOX 13 -------+ Does this mean two's complement? Is there a definition of "pure binary numeration system?" +------- END BOX 13 -------+ _________________________ 9) See _dcl.type.simple_ regarding the correspondence between types and the sequences of type-specifiers that designate them. 10) This implies that unsigned arithmetic does not overflow because a result that cannot be represented by the resulting unsigned integer type is reduced modulo the number that is one greater than the largest value that can be represented by the resulting unsigned integer type. 11) Using a bool value in ways described by this International Stan dard as ``undefined,'' such as by examining the value of an uninitial ized automatic variable, might cause it to behave as if is neither true nor false. 12) Therefore, enumerations (_dcl.enum_) are not integral; however, enumerations can be promoted to int, unsigned int, long, or unsigned long, as specified in _conv.prom_. 9 There are three floating point types: float, double, and long double. The type double provides at least as much precision as float, and the type long double provides at least as much precision as double. The set of values of the type float is a subset of the set of values of the type double; the set of values of the type double is a subset of the set of values of the type long double. The value representation of floating-point is implementation-defined. Integral and floating types are collectively called arithmetic types. Specializations of the standard template numeric_limits (_lib.support.limits_) shall specify the largest and smallest values of each arithmetic types for an implementation. 10The void type has an empty set of values. It is used as the return type for functions that do not return a value. The void type is not an object type and objects of type void shall not be created. Any expression can be explicitly converted to type void (_expr.cast_); the resulting expression shall be used only as an expression statement (_stmt.expr_), as the left operand of a comma expression (_expr.comma_), or as a second or third operand of ?: (_expr.cond_). 11[Note: Even if the implementation defines two or more basic types to have the same value representation, they are nevertheless different types. ] 3.9.2 Compound types [basic.compound] 1 Compound types can be constructed from the fundamental types in the following ways: --arrays of objects of a given type, _dcl.array_; --functions, which have parameters of given types and return void or references or objects of a given type, _dcl.fct_; --pointers to void or objects or functions (including static members of classes) of a given type, _dcl.ptr_; --references to objects or functions of a given type, _dcl.ref_; --constants, which are values of a given type, _dcl.type_; --classes containing a sequence of objects of various types (_class_), a set of functions for manipulating these objects (_class.mfct_), and a set of restrictions on the access to these objects and func tions, _class.access_; --unions, which are classes capable of containing objects of different types at different times, _class.union_; --pointers to non-static13) class members, which identify members of a _________________________ 13) Static class members are objects or functions, and pointers to them are ordinary pointers to objects or functions. given type within objects of a given class, _dcl.mptr_. 2 These methods of constructing types can be applied recursively; restrictions are mentioned in _dcl.ptr_, _dcl.array_, _dcl.fct_, and _dcl.ref_. 3 A pointer to objects of type T is referred to as a "pointer to T." [Example: a pointer to an object of type int is referred to as "pointer to int" and a pointer to an object of class X is called a "pointer to X." ] Except for pointers to static members, text refer ring to "pointers" does not apply to pointers to members. Pointers to incomplete types are allowed although there are restrictions on what can be done with them (_basic.types_). The value representation of pointer types is implementation-defined. Pointers to cv-qualified and cv-unqualified versions (_basic.type.qualifier_) of layout-compatible types shall have the same value representation and alignment require ments (_basic.types_). 4 Objects of cv-qualified (_basic.type.qualifier_) or cv-unqualified type void* (pointer to void), can be used to point to objects of unknown type. A void* shall be able to hold any object pointer. A cv-qualified or cv-unqualified (_basic.type.qualifier_) void* shall have the same representation and alignment requirements as a cv- qualified or cv-unqualified char*. 5 Except for pointers to static members, text referring to "pointers" does not apply to pointers to members. 3.9.3 CV-qualifiers [basic.type.qualifier] 1 A type mentioned in _basic.fundamental_ and _basic.compound_ is a cv- unqualified type. Each cv-unqualified fundamental type (_basic.fundamental_) has three corresponding cv-qualified versions of its type: a const-qualified version, a volatile-qualified version, and a const-volatile-qualified version. The term object type (_intro.object_) includes the cv-qualifiers specified when the object is created. The presence of a const specifier in a decl-specifier-seq declares an object of const-qualified object type; such object is called a const object. The presence of a volatile specifier in a decl-specifier-seq declares an object of volatile-qualified object type; such object is called a volatile object. The presence of both cv-qualifiers in a decl-specifier-seq declares an object of const- volatile-qualified object type; such object is called a const volatile object. The cv-qualified or cv-unqualified versions of a type are distinct types; however, they shall have the same representation and alignment requirements (_basic.types_).14) 2 A compound type (_basic.compound_) is not cv-qualified by the cv- qualifiers (if any) of the type from which it is compounded. However, _________________________ 14) The same representation and alignment requirements are meant to imply interchangeability as arguments to functions, return values from functions, and members of unions. any cv-qualifiers that appear in an array declaration apply to the array element type, not the array type (_dcl.array_). 3 Each non-function, non-static, non-mutable member of a const-qualified class object is const-qualified, each non-function, non-static member of a volatile-qualified class object is volatile-qualified and simi larly for members of a const-volatile class. See _dcl.fct_ and _class.this_ regarding cv-qualified function types. 4 There is a (partial) ordering on cv-qualifiers, so that a type can be said to be more cv-qualified than another. Table 1 shows the rela tions that constitute this ordering. Table 1--relations on const and volatile +----------+ no cv-qualifier < const no cv-qualifier < volatile no cv-qualifier |< const volatile const < | const volatile volatile < | const volatile +----------+ 5 In this International Standard, the notation cv (or cv1, cv2, etc.), used in the description of types, represents an arbitrary set of cv- qualifiers, i.e., one of {const}, {volatile}, {const, volatile}, or the empty set. Cv-qualifiers applied to an array type attach to the underlying element type, so the notation "cv T," where T 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. 3.9.4 Type names [basic.type.name] 1 [Note: Fundamental and compound types can be given names by the type def mechanism (_dcl.typedef_), and families of types and functions can be specified and named by the template mechanism (_temp_). ] 3.10 Lvalues and rvalues [basic.lval] 1 Every expression is either an lvalue or an rvalue. 2 An lvalue refers to an object or function. Some rvalue expressions-- those of class or cv-qualified class type--also refer to objects.15) _________________________ 15) Expressions such as invocations of constructors and of functions that return a class type refer to objects, and the implementation can invoke a member function upon such objects, but the expressions are not lvalues. 3 [Note: some builtin operators and function calls yield lvalues. [Example: if E is an expression of pointer type, then *E is an lvalue expression referring to the object or function to which E points. As another example, the function int& f(); yields an lvalue, so the call f() is an lvalue expression. ] ] 4 [Note: some builtin operators expect lvalue operands. [Example: builtin assignment operators all expect their left hand operands to be lvalues. ] Other builtin operators yield rvalues, and some expect them. [Example: the unary and binary + operators expect rvalue argu ments and yield rvalue results. ] The discussion of each builtin operator in clause _expr_ indicates whether it expects lvalue operands and whether it yields an lvalue. ] 5 Constructor invocations and calls to functions that do not return ref erences are always rvalues. User defined operators are functions, and whether such operators expect or yield lvalues is determined by their type. 6 Whenever an lvalue appears in a context where an lvalue is not expected, the lvalue is converted to an rvalue; see _conv.lval_, _conv.array_, and _conv.func_. 7 The discussion of reference initialization in _dcl.init.ref_ and of temporaries in _class.temporary_ indicates the behavior of lvalues and rvalues in other significant contexts. 8 Class rvalues can have cv-qualified types; non-class rvalues always have cv-unqualified types. Rvalues always have complete types or the void type; in addition to these types, lvalues can also have incom plete types. 9 An lvalue for an object is necessary in order to modify the object except that an rvalue of class type can also be used to modify its referent under certain circumstances. [Example: a member function called for an object (_class.mfct_) can modify the object. ] 10Functions cannot be modified, but pointers to functions can be modifi able. 11A pointer to an incomplete type can be modifiable. At some point in the program when this pointer type is complete, the object at which the pointer points can also be modified. 12Array objects cannot be modified, but their elements can be modifi able. 13The referent of a const-qualified expression shall not be modified (through that expression), except that if it is of class type and has a mutable component, that component can be modified (_dcl.type.cv_). 14If an expression can be used to modify its object, it is called modi fiable. A program that attempts to modify an object through a nonmod ifiable lvalue or rvalue expression is ill-formed. 15If a program attempts to access the stored value of an object through an lvalue of other than one of the following types the behavior is undefined: --the dynamic type of the object, --a cv-qualified version of the declared type of the object, --a type that is the signed or unsigned type corresponding to the declared type of the object, --a type that is the signed or unsigned type corresponding to a cv- qualified version of the declared type of the object, --an aggregate or union type that includes one of the aforementioned types among its members (including, recursively, a member of a sub aggregate or contained union), --a type that is a (possibly cv-qualified) base class type of the declared type of the object, --a char or unsigned char type.16) _________________________ 16) The intent of this list is to specify those circumstances in which an object may or may not be aliased.