CBase-derived classes and two-phase construction

This document describes the need for two-phase construction and how to use second phase constructors.

When the construction of an object cannot leave (except for out-of-memory for the allocation of the object itself), then it is appropriate to use the conventional C++ constructor, which is automatically invoked by new.

When the construction of an object may leave, then the object must be pushed to the clean-up stack, or a pointer to the object must be stored in an object that would be cleaned up if a leave occurred, before any part of the construction function is invoked that may leave. To allow this to happen, construction steps that can leave, are performed not in the C++ constructor, but in another initialization functions, referred to as a second phase constructor.

Thus, the general sequence for two-phase construction is:

  1. allocate memory for the object (and leave if out of memory) using new

  2. optionally define a C++ constructor to perform any construction that cannot leave

  3. push a pointer to the object, or store a pointer to it in a class with cleanup support

  4. use the second phase constructor to perform any part of the construction that might leave

Note that:

  • The whole sequence is usually encapsulated in static member functions called NewL(), and NewLC() (which additionally leaves the created object on the clean-up stack).

  • Abstract classes are not intended to be instantiated, and so have no NewLC() or NewL(), only a second phase constructor.

  • Step 2 is optional, because all such construction can be performed by the second phase constructor. The C++ constructor is only necessary when the class is immediately derived from a base class whose default C++ constructor cannot be used. In this case, the derived class must call the base class’s constructor with appropriate parameters.

  • It is conventional for the second phase constructor to be called ConstructL().