Symbian class conventions

The fundamental rules for instantiating and using Symbian classes.

T classes

Symbian C++ defines several class types, each of which has different characteristics, such as where objects may be created (on the heap, on the stack) and how those objects should later be cleaned up. The conventions make the creation, use and destruction of objects more straightforward. Symbian uses a simple naming convention which prefixes the class name with a letter (T, C, R, or M).

T classes are simple classes that behave much like the C++ built-in types. For this reason, they are prefixed with the same letter as the typedefs for the built-in C++ types.

Consider the following simple function:
void LeavingFunctionL()
  {
  // T object declared on the stack.
  TExample example;

  // Call a function that can leave.
  DoSomethingL();
  }
When Symbian C++ was initially created, the destructor of a stack-based object was not called in the event of a leave occurring. The T prefix was used to indicate a type of class that was safe to declare on the stack, in other words, a class that didn’t contain data members that required cleanup via a destructor. As a consequence, T classes do not have destructors.

C classes

C classes are only ever allocated on the heap. Unlike T classes, C classes own pointers to other objects, and have a destructor to clean up these member variables.

A C class uses public inheritance, and must ultimately derive from CBase. A C class never inherits directly from more than one C class. This is to avoid the problems that can arise from multiple inheritance of implementation in C++.

On instantiation, a C class typically needs to call code which may fail. A good example is instantiation of an object that performs a memory allocation, which fails if there is insufficient memory available. This kind of failure is handled by what is called a leave, and is discussed in more detail in Symbian exception handling. A constructor should never be able to leave, because this can cause memory leaks. To avoid this, C classes use an idiom called Two-phase construction. This means that the constructor is guaranteed not to leave and that any initialization that might leave is deferred until a second phase constructor, usually called ConstructL().

R classes

The R which prefixes an R class indicates that it holds an external resource handle, for example a handle to a server session. R classes are often small, and usually contain no other member data besides the resource handle.

While a C class directly allocates resources (for example memory), R classes cause the indirect allocation of resources. For example, in order to open a file the method RFile::Open() would be used. The RFile class does not itself open the file and consequently use resources directly. Instead, it has a handle to an object managed by the File Server, which would directly open the file and use the resources.

Unlike the C class type, there is no equivalent RBase class (although many R classes derive from RHandleBase – this is especially important for resources which may need to be shared across threads and processes). A typical R class has a simple constructor and an initialization method typically called Open() that must be called after construction to set up the associated resource and store its handle as a member variable of the R class object.

An R class must also have a method that can be used to release the resource (via the handle). Although in theory this cleanup function can be named anything, by convention it is almost always called Close(). To ensure that Close() is called even if a leave occurs, R objects often need to be added to the cleanup stack using the function CleanupClosePushL(). See Using the cleanup stack for an example.

M classes

An M class is an abstract interface class that declares pure virtual functions and has no member data. The M prefix stands for mixin, indicating that the class is used for defining an interface. In Symbian C++, M classes are often used to define callback interfaces or observer classes. The only form of multiple inheritance encouraged on Symbian C++ is that involving multiple M classes. Multiple inheritance is discussed further in Multiple inheritance and interfaces.

Copyright note

The material in this topic is based with permission on a Symbian Foundation wiki article Class Types & Declarations which is part of the series The Fundamentals of Symbian C++. The version used was that available at http://developer.symbian.org/ on 3 November 2010. The content in this page is licensed under the Creative Commons Attribution-Share Alike 2.0 UK: England & Wales License (http://creativecommons.org/licenses/by-sa/2.0/uk).