______________________________________________________________________

  3   Basic concepts                                   [basic]

  ______________________________________________________________________

1 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.

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_).

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_).  Every name
  is introduced in some contiguous portion  of  program  text  called  a
  declarative  region  (_basic.scope_), 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 por­
  tion of program text called its scope (_basic.scope_).   To  determine
  the scope of a declaration, it is sometimes convenient to refer to the
  potential scope of a declaration.  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  (contain­
  ing) declarative region.

6 For example, in

          int j = 24;

          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.

7 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.

8 Two names denote the same entity 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.

9 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 The following, for example, 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

4 In  some circumstances, C++ implementations generate definitions auto­
  matically.  These definitions include default constructors, copy  con­
  structors, assignment operators, and destructors.  For example, given
          struct C {
              string s;    // string is the standard library class (_lib.string_)
          };

          main()
          {
              C a;
              C b=a;
              b=a;
          }
  the implementation will generate functions to make the definition 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() { }
          };

5 A class name can also implicitly be declared  by  an  elaborated-type-
  specifier (_dcl.type.elab_).

  3.2  One definition rule                               [basic.def.odr]

  +-------                 BEGIN BOX 1                -------+
  This is still very much under review by the Committee.
  +-------                  END BOX 1                 -------+

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, 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)  the  implementation  can  generate it.  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 virtual function
  is neither called nor defined, 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 Exactly one definition in a program is required for a non-local  vari­
  able  with static storage duration, unless it has a builtin type or is
  an aggregate and also is unused or used only as  the  operand  of  the
  sizeof operator.

  +-------                 BEGIN BOX 3                -------+
  This is still uncertain.
  +-------                  END BOX 3                 -------+

4 At  least  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  ref­
  erence 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                 -------+

  For  example  the  following complete translation unit is well-formed,
  even though it never defines X:
          struct X;      // declare X is a struct type
          struct X* x1;  // use X in pointer formation
          X* x2;         // use X in pointer formation

5 There can be more than one definition of a named enumeration type in a
  program  provided that each definition appears in a different transla­
  tion unit and the names and values of the enumerators are the same.

  +-------                 BEGIN BOX 6                -------+
  This will need to be revisited when the ODR is made more precise
  +-------                  END BOX 6                 -------+

6 There can be more than one definition of a class  type  in  a  program
  provided  that each definition appears in a different translation unit
  and the definitions describe the same type.

7 No diagnostic is required for a violation of the ODR rule.

  +-------                 BEGIN BOX 7                -------+
  This will need to be revisited when the ODR is made more precise
  +-------                  END BOX 7                 -------+

  3.3  Declarative regions and scopes                      [basic.scope]

1 The name look up rules are summarized in _class.scope_.

  3.3.1  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, condition, and controlling
  expression parts of if, while, for, and switch statments are local  to
  the  if,  while,  for,  or  switch statement (including the controlled
  statement), and shall not be redeclared in a subsequent  condition  or
  controlling expression of that statement nor in the outermost block of
  the controlled statement.

5 Names declared in the outermost block of the controlled statement of a
  do statement shall not be redeclared in the controlling expression.

  3.3.2  Function prototype scope                    [basic.scope.proto]

1 In a function declaration, or in any of 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 function declarator.

  3.3.3  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.4  Namespace scope                         [basic.scope.namespace]

1 A  name  declared  in a named or unnamed namespace (_basic.namespace_)
  has namespace 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.   A namespace member can also be used after
  the :: scope resolution operator (_expr.prim_) applied to the name  of
  its namespace.

2 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.5  Class scope                                 [basic.scope.class]

1 The  name of a class member is local to its class and can be used only
  in:

  --the  scope  of  that  class  (_class.scope0_)  or  a  class  derived
    (_class.derived_) from that 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_).

2 The scope of names introduced by friend declarations is  described  in
  _namespace.def_.

3 The scope rules for classes are summarized in _class.scope0_.

  3.3.6  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.

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
  _class.scope0_.   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.

5 The region in which a name is visible is called the reach of the name.

  +-------                 BEGIN BOX 8                -------+
  The term 'reach' is defined here but never used.  More work is  needed
  with the "descriptive terminology".
  +-------                  END BOX 8                 -------+

  3.3.7  Explicit qualification                     [basic.scope.exqual]

  +-------                 BEGIN BOX 9                -------+
  The information in this section is very similar to the one provided in
  _namespace.qual_.    The   information   in   these    two    sections
  (_basic.scope.exqual_  and _namespace.qual_) should be consolidated in
  one place.
  +-------                  END BOX 9                 -------+

1 A name hidden by a nested declarative  region  or  derived  class  can
  still  be  used  when  it  is qualified by its class or namespace name
  using the :: operator (_expr.prim_, _class.static_,  _class.derived_).
  A  hidden  global scope name can still be used when it is qualified by
  the unary :: operator (_expr.prim_).

  3.3.8  Elaborated type specifier                    [basic.scope.elab]

1 A class name or enumeration name can be  hidden  by  the  name  of  an
  object, function, or enumerator in local, class or namespace scope.  A
  hidden class name can still be used when appropriately  prefixed  with
  class, struct, or union (_dcl.type_), or when followed by the :: oper­
  ator.  A hidden enumeration name can still be used when  appropriately
  prefixed with enum (_dcl.type_).  For example:

          class A {
          public:
              static int n;
          };

          main()
          {
              int A;

              A::n = 42;          // OK
              class A a;          // OK
              A b;                // ill-formed: A does not name a type
          }
  The   scope  of  class  names  first  introduced  in  elaborated-type-
  specifiers is described in (_dcl.type.elab_).

  3.3.9  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.  For example,
      int x = 12;
      { int x = x; }

2 Here the second x is initialized with its own (unspecified) value.

3 For the point of declaration for an enumerator, see _dcl.enum_.

4 For the point of declaration of a function first declared in a  friend
  declaration, see _class.friend_.

5 For  the  point  of declaration of a class first declared in an elabo­
  rated-type-specifier or in a friend declaration, see  _dcl.type.elab_.

6 A  nonlocal name remains visible up to the point of declaration of the
  local name that hides it.  For example,
      const int  i = 2;
      { int  i[i]; }
  declares a local array of two integers.

7 The point of instantiation of a template is described in  _temp.inst_.

  3.4  Name look up                                        [class.scope]

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.   This  section  discusses
  name  look  up  in  lexical scope only; _basic.link_ discusses linkage
  issues.  The notions of name hiding and point of declaration are  dis­
  cussed in _basic.scope_.

2 Name  look  up associates the use of a name with a visible 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 declaration with a name if  it  finds  the
  name  to  be a function name; in this case, all the declarations shall
  be found in the same scope (_class.member.lookup_);  the  declarations
  are  said  to form a set of overloaded functions (_over.load_).  Over­
  load resolution (_over.match_) takes place after name look up has suc­
  ceeded.   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 overload resolution (if
  applicable) and access checking  have  succeeded  are  the  attributes
  introduced  by  the name's declaration used further in expression pro­
  cessing (_expr_).

3 A name used in the global scope outside  of  any  function,  class  or
  user-declared namespace, shall be declared before it is used in global
  scope or be a name introduced by a using directive  (_namespace.udir_)
  that appears in global scope before the name is used.

4 A  name  specified  after  a nested-name-specifier is looked up in the
  scope of the class or namespace denoted by the  nested-name-specifier;
  see  _expr.prim_  and  _namespace.qual_.  A name prefixed by the unary
  scope operator :: (_expr.prim_) is looked up in global scope.  A  name
  specified after the . operator or -> operator of a class member access
  is looked up as specified in _expr.ref_.

5 A name that is not qualified in any of the ways  described  above  and
  that  is used in a namespace outside of the definition of any function
  or class shall be declared before its use in that namespace or in  one
  of  its  enclosing  namespaces  or, be introduced by a using directive
  (_namespace.udir_) visible at the point the name is used.

6 A name that is not qualified in any of the ways  described  above  and
  that  is  used  in  a  function  that  is  not a class member 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 the namespace enclosing the function definition or  in  one  of
  its  enclosing namespaces or, shall be introduced by a using directive
  (_namespace.udir_) visible at the point the name is used.

7 A name that is not qualified in any of the ways  described  above  and
  that is used in the definition of a class X outside of any inline mem­
  ber function or nested class definition shall be declared  before  its
  use  in  class  X  (_class.scope0_)  or be a member of a base class of
  class X (_class.derived_) or, if X  is  a  nested  class  of  class  Y
  (_class.nest_),  shall be declared before the definition of class X in
  the enclosing class Y or in Y's enclosing classes or, if X is a  local
  class  (_class.local_),  shall  be  declared  before the definition of
  class X in a block enclosing the definition of class X  or,  shall  be
  declared before the definition of class X in a namespace enclosing the
  definition of class X or, be introduced by a using directive  (_names­
  pace.udir_)  visible  at  the  point the name is used.  _class.scope0_
  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 defini­
  tions.

8 A name that is not qualified in any of the ways  described  above  and
  that is used in a function that is a member function (_class.mfct_) of
  class X shall be declared 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 (_class.mem_)  or  a  member  of  a  base  class  of  class  X
  (_class.derived_)   or,   if   X   is   a  nested  class  of  class  Y
  (_class.nest_), shall be a member of the enclosing class Y or a member
  of  Y's  enclosing  classes or, if X is a local class (_class.local_),
  shall be declared before the definition of class X in a block  enclos­
  ing  the definition of class X or, shall be declared before the member
  function definition in a namespace enclosing the member function defi­
  nition or, be introduced by a using directive (_namespace.udir_) visi­
  ble at the point the name is used.   _class.mfct_  and  _class.static_
  further  describe the restrictions on the use of names in member func­
  tion definitions.  _class.nest_ further describes the restrictions  on
  the  use  of names in the scope of nested classes.  _class.local_ fur­
  ther describes the restrictions on the use of  names  in  local  class
  definitions.

9 For  a  friend function (_class.friend_) defined inline in the defini­
  tion of the class granting friendship, name  look  up  in  the  friend
  function  definition  for  a  name that is not qualified in any of the
  ways described above proceeds as described in member function  defini­
  tions.   If  the  friend function is not defined in the class granting
  friendship, name look up in the friend function definition for a  name
  that  is  not qualified in any of the ways described above proceeds as
  described in nonmember function definitions.

10A name that is not qualified in any of the ways  described  above  and
  that  is  used in a function parameter-declaration-clause as a default
  argument (_dcl.fct.default_) or that  is  used  in  a  function  ctor-
  initializer  (_class.base.init_)  is looked up as if the name was 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 ctor-initializers.  _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.

11A  name  that  is not qualified in any of the ways described above and
  that is used in the initializer expression of a static member of class
  X  (_class.static.data_) shall be a member of class X (_class.mem_) or
  a member of a base class of class X (_class.derived_) or, if  X  is  a
  nested  class  of  class  Y  (_class.nest_),  shall be a member of the
  enclosing class Y or a member of Y's enclosing classes or, be declared
  before  the  static  member  definition in the namespace enclosing the
  static member definition or in one of its enclosing namespaces or,  be
  introduced  by  a  using  directive  (_namespace.udir_) visible at the
  point the name is used.   _class.static.data_  further  describes  the

  restrictions  on  the use of names in the initializer expression for a
  static data member.  _class.nest_ further describes  the  restrictions
  on the use of names in nested class definitions.

12In  all  cases, the scopes are searched for a declaration in the order
  listed in each of the respective category above and name look up  ends
  as soon as a declaration is found for the name.

  +-------                BEGIN BOX 10                -------+
  This subclause should probably say something about look up in template
  definitions.
  +-------                 END BOX 10                 -------+

  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,
  function,  type, template, or value as a name introduced by a declara­
  tion 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 class (_class_) or enumeration (_dcl.enum_) or an enumerator; or

  --a template (_temp_).  In addition, a name of class scope has  exter­
    nal linkage if the name of the class has external linkage.

  +-------                BEGIN BOX 11                -------+
  What  is  the  linkage  of unnamed classes and their members?  Unnamed
  enumeration and their enumerators?
  +-------                 END BOX 11                 -------+

5 The name of a function  declared  in  a  block  scope  or  a  variable
  declared  extern  in  a  block  scope  has linkage, either internal or
  external to match the linkage of prior  visible  declarations  of  the
  name  in  the  same translation unit, but if there is no prior visible
  declaration it has external linkage.

6 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.  For example:
          void f()
          {
              struct A { int x; };       // no linkage
              extern A a;                // ill-formed
          }
  This implies that names with no linkage cannot  be  used  as  template
  arguments (_temp.arg_).

7 Two  names that are the same and that are declared in different scopes
  shall denote the same object, function, type, enumerator, or  template
  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 or function templates, the function
    types are identical for purposes of overloading.

8 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
  such  types  can  differ  by  the presence or absence of a major array
  bound (_dcl.array_). A violation of this rule does not require a diag­
  nostic.

  +-------                BEGIN BOX 12                -------+
  This  needs  to  specified  more  precisely to deal with function name
  overloading.

  +-------                 END BOX 12                 -------+

9 Linkage to non-C++ declarations  can  be  achieved  using  a  linkage-
  specification (_dcl.link_).

  3.6  Start and termination                               [basic.start]

  3.6.1  Main function                                [basic.start.main]

1 A  program  shall  contain global a function called main, which is the
  designated start of the program.

2 This function is not predefined by the compiler, it  cannot  be  over­
  loaded,  and  its  type is implementation dependent.  The two examples
  below are allowed on any implementation.  It is recommended  that  any
  further  (optional)  parameters  be  added  after  argv.  The function
  main() can be defined as
          int main() { /* ... */ }
  or
          int main(int argc, char* argv[]) { /* ... */ }
  In the latter form argc shall be the number of arguments passed to the
  program  from  an 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 zero-terminated
  strings; and argv[0] shall be the pointer to the initial character  of
  a  zero-terminated  string that represents the name used to invoke the
  program or "".  It is guaranteed that argv[argc]==0.

3 The function main() shall not be called from within  a  program.   The
  linkage  (_basic.link_)  of  main()  is implementation dependent.  The
  address of main() shall not be taken and main() shall not be  declared
  inline or static.  The name main is not otherwise reserved.  For exam­
  ple, 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 local variables (_class.dtor_).  The argument value is returned to
  the program's environment as the value of the program.

5 A return statement in main() has the effect of leaving the main  func­
  tion  (destroying  any  local  variables)  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 execut­
  ing
          return 0;

  3.6.2  Initialization of non-local objects          [basic.start.init]

  +-------                BEGIN BOX 13                -------+
  This is still under active discussion by the committee.
  +-------                 END BOX 13                 -------+

1 The initialization of  nonlocal  static  objects  (_basic.stc_)  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 default initialization of all static objects to
  zero  (_dcl.init_)  is  performed  before  any  other  initialization.
  Static objects initialized with  constant  expressions  (_expr.const_)
  are  initialized before any dynamic (that is, run-time) initialization
  takes place.  The order of initialization of nonlocal  static  objects
  defined in the same translation unit is the order in which their defi­
  nition appears in the 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 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  initialized  before  an
  atexit()  call until after the function 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 static  objects  and  without  calling  the  functions
  passed to atexit().

  3.7  Storage duration and lifetime                         [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_)  and  with  temporaries
  (_class.temporary_).  The dynamic storage duration is associated  with
  objects created with operator new (_expr.new_).

3 The  storage class specifiers static, auto, and mutable 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.

5 The  lifetime  of  an object is a runtime property of the object.  The
  implementation controls the lifetime of objects with static  or  auto­
  matic  storage  duration.  Users  control the lifetime of objects with
  dynamic storage duration.

  +-------                BEGIN BOX 14                -------+
  What is the lifetime of an object?  When is it well-formed  and  well-
  defined  to  access  an object?  When is it ill-formed or undefined to
  access an object?  Subclause 1.5 used to  say:  "The  lifetime  of  an
  object  starts  after any required initialization (8.5) has completed.
  For objects with destructor, it ends when destruction  starts."   This
  description  is being worked out by the Core Language WG.  In particu­
  lar, a better description is needed to take into account what  happens
  when users play tricks with objects' lifetime.
  +-------                 END BOX 14                 -------+

6 The lifetime of temporaries is described in (_class.temporary_).

  3.7.1  Static storage duration                      [basic.stc.static]

1 All  non-local  objects have static storage duration.  The storage for
  these objects can last for the entire duration of the program.   These
  objects    are    initialized    and   destroyed   as   described   in
  _basic.start.init_ and _basic.start.term_.

2 Note that 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.

  +-------                BEGIN BOX 15                -------+
  This awaits committee action on the ``as-if'' rule.
  +-------                 END BOX 15                 -------+

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.

5 Temporaries created at global scope have 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 have automatic  storage  duration.   The  storage  for
  these objects lasts until the block in which they are created exits.

2 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.

4 Temporaries created in block scope have automatic storage duration.

  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 can be static class member  functions  or  global
  functions.   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_).

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 pointer to or within any other currently allocated  storage.   The
  results of dereferencing a pointer returned as a request for zero size
  are undefined.1)

3 If  an allocation function is unable to obtain an appropriate block of
  storage, it can invoke  the currently installed  new_handler2)  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 Like  allocation functions, deallocation functions can be static class
  member functions or global functions.

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 can be added but deallocation functions shall
  not be overloaded.

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
  _________________________
  1) 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.
  2) 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_).

  a zero argument).  If the value of the first  argument  is  null,  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-null, the value of a  pointer  that  refers  to
  deallocated  space  is  indeterminate.  The effect of dereferencing an
  indeterminate pointer value is undefined.3)

  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.7.5  The mutable keyword                         [basic.stc.mutable]

1 The keyword mutable is grammatically a storage class specifier but  is
  unrelated  to  the  storage duration (lifetime) of the class member it
  describes.   The  mutable  keyword  is  described   in   _basic.lval_,
  _expr.ref_, _dcl.stc_ and _dcl.type.cv_.

  3.8  Types                                               [basic.types]

1 There  are  two  kinds of types: fundamental types and compound types.
  Types can describe objects (_intro.object_),  references  (_dcl.ref_),
  or functions (_dcl.fct_).

2 Object   types   have   alignment  requirements  (_basic.fundamental_,
  _basic.compound_). The alignment of an object type is  an  implementa­
  tion-dependent integer value representing a number of bytes; an object
  is allocated at an address that is divisible by the alignment  of  its
  object type.

3 Arrays  of  unknown  size  and classes that have been declared but not
  defined are called incomplete types because the size and layout of  an
  instance of the type is unknown.  Also, the void type is an incomplete
  type; it represents an empty set of values.  No objects can be defined
  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 complete type;

4 A  class  type  (such  as class X) can 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 can be incomplete
  at one point in a translation unit and complete later  on;  the  array
  _________________________
  3) On some architectures, it causes a system-generated runtime  fault.

  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 declaration to be an
  array of unknown size, cannot be completed.

5 Expressions that have incomplete type are prohibited in some contexts.
  For 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 Clauses  _expr_ and _stmt.stmt_ indicate in more details in which con­
  texts incomplete types are allowed or prohibited.

7 If two types T1 and T2 are the same type, then T1 and T2  are  layout-
  compatible  types.   Layout-compatible  enumerations  are described in
  _dcl.enum_.   Layout-compatible   POD-structs   and   POD-unions   are
  described in _class.mem_.

  3.8.1  Fundamental types                           [basic.fundamental]

1 There  are several fundamental types.  Specializations of the standard
  template numeric_limits (_lib.support.limits_) specify the largest and
  smallest values of each for an implementation.

2 Objects  declared  as  characters  char) are large enough to store any
  member of the implementation's basic character set.   If  a  character
  from  this set is stored in a character variable, its value is equiva­
  lent to the integer code of that  character.   It  is  implementation-
  specified  whether a char object can take on 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_).  In any par­
  ticular implementation, a plain char object can  take  on  either  the

  same  values as a signed char or an unsigned char; which one is imple­
  mentation-defined.

3 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.

4 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 other­
  wise make any of them equal in storage size.  Plain ints have the nat­
  ural  size  suggested  by  the  machine architecture; the other signed
  integer types are provided to meet special needs.

5 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 type.4) The range
  of nonnegative values of a signed integer type is a  subrange  of  the
  corresponding  unsigned  integer  type,  and the representation of the
  same value in each type is the same.

6 Unsigned integers, declared unsigned, obey the laws of arithmetic mod­
  ulo  2n  where  n  is the number of bits in the representation of that
  particular size of integer.  This  implies  that  unsigned  arithmetic
  does not overflow.

7 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 has the same
  size, signedness, and alignment requirements (_intro.memory_)  as  one
  of the other integral types, called its underlying type.

8 Values of type bool can be  either  true  or  false.5)  There  are  no
  signed,  unsigned,  short, or long bool types or values.  As described
  below, bool values behave as integral types.  Thus, for example,  they
  participate  in  integral  promotions (_conv.prom_, _expr.type.conv_).
  Although values of type bool generally behave as signed integers,  for
  example  by  promoting (_conv.prom_) to int instead of unsigned int, a
  bool value can successfully be stored in a bit-field of any  (nonzero)
  size.

  _________________________
  4) See _dcl.type.simple_ regarding the  correspondence  between  types
  and the sequences of type-specifiers that designate them.
  5) Using a bool value in ways described by this International Standard
  as ``undefined,'' such as by examining the value of  an  uninitialized
  automatic variable, might cause it to behave as if is neither true nor
  false.

9 Types  bool,  char, wchar_t, and the signed and unsigned integer types
  are collectively called integral types.  A synonym for  integral  type
  is integer type.  Enumerations (_dcl.enum_) are not integral, but they
  can be promoted (_conv.prom_) to int, unsigned int, long, or  unsigned
  long.   The  representations  of integral types shall define values by
  use of  a pure binary numeration system.

  +-------                     BEGIN BOX 16                     -------+
  Does this mean two's complement?  Is there a definition of pure binary
  numeration system?
  +-------                      END BOX 16                      -------+

10There  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.  Inte­
  gral and floating types are collectively called arithmetic types.

11The void type specifies an empty set of values.  It  is  used  as  the
  return type for functions that do not return a value.  Objects of type
  void shall not be declared.  Any expression  can  be  explicitly  con­
  verted  to  type  void  (_expr.cast_); the resulting expression can 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_).

12Even if the implementation defines two or more basic types to have the
  same representation, they are nevertheless different types.

  3.8.2  Compound types                                 [basic.compound]

1 There  is a conceptually infinite number of compound types 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  objects
    of a given type, _dcl.fct_;

  --pointers  to  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-static6) class members, which identify members of a
    given type within objects of a given class, _dcl.mptr_.

2 In general, these methods of constructing types can be applied  recur­
  sively;   restrictions   are   mentioned  in  _dcl.ptr_,  _dcl.array_,
  _dcl.fct_, and _dcl.ref_.

3 A pointer to objects of a type T is referred to as  a  pointer  to  T.
  For  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.  Pointers to incomplete types are allowed although there
  are restrictions on  what  can  be  done  with  them  (_basic.types_).
  Pointers to qualified or unqualified versions (_basic.type.qualifier_)
  of layout-compatible types shall  have  the  same  representation  and
  alignment requirements (_basic.types_).

4 Objects  of  cv-qualified (_basic.type.qualifier_) or unqualified type
  void* (pointer to void), can be used to point to  objects  of  unknown
  type.   A  void* has enough bits to hold any object pointer.  A quali­
  fied or unqualified (_basic.type.qualifier_) void* shall have the same
  representation  and  alignment requirements as a qualified or unquali­
  fied char*.

5 Except for pointers to static members, text referring to pointers does
  not apply to pointers to members.

  3.8.3  CV-qualifiers                            [basic.type.qualifier]

1 Any  type  so  far mentioned is an unqualified type.  Each unqualified
  fundamental type (_basic.fundamental_) has three corresponding  quali­
  fied  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 unqualified versions of a type
  are distinct types; however, they have  the  same  representation  and
  alignment    requirements    (_basic.types_).7)    A   compound   type
  (_basic.compound_) is not cv-qualified by the cv-qualifiers  (if  any)
  of  the  type  from which it is compounded.  However, an array type is
  considered to be cv-qualified by  the  cv-qualifiers  of  its  element
  type.   Moreover, when an array type is cv-qualified, its element type
  _________________________
  6) Static class members are objects or functions, and pointers to them
  are ordinary pointers to objects or functions.
  7) The same representation and alignment requirements are meant to im­
  ply interchangeability as arguments to functions, return  values  from
  functions, and members of unions.

  is considered to have the same cv-qualifiers (_dcl.array_).

2 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.

3 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             |
             +-----------------------------------------------+

4 In this document, 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 ele­
  ment 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.8.4  Type names                                    [basic.type.name]

1 Fundamental and compound types can be given names by the typedef mech­
  anism (_dcl.typedef_), and families of  types  and  functions  can  be
  specified and named by the template mechanism (_temp_).

  3.9  Lvalues and rvalues                                  [basic.lval]

1 Every expression is either an lvalue or 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.8)

3 Some builtin operators and function calls yield lvalues.  For example,
  if E is an expression of pointer type, then *E is an lvalue expression
  _________________________
  8) Expressions such as invocations of constructors  and  of  functions
  that  return a class type do in some sense refer to an object, and the
  implementation can invoke a member function upon such objects, but the
  expressions are not lvalues.

  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 Some builtin operators expect lvalue operands, for example the builtin
  assignment  operators  all expect their left hand operands to be lval­
  ues.  Other builtin operators yield rvalues,  and  some  expect  them.
  For  example  the unary and binary + operators expect rvalue arguments
  and yield rvalue results.  The discussion of each builtin operator  in
  _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 qualified types; non-class rvalues always have
  unqualified types.  Rvalues always have complete  types  or  the  void
  type; lvalues may have incomplete types.

9 An  lvalue for an object is generally necessary in order to modify the
  object.  An rvalue of class type can also be used to modify its refer­
  ent  under  certain  circumstances.   For  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.

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.