SOM's OOP Model from the SOMobjects Developer Toolkit

Written by Gordon Zeglinski

Introduction
This column deviates from the usual C++ stuff; instead, we will be exploring SOM's OOP model. More precisely, the SOMobjects Developer Toolkit, which ships with SOM 2 and DSOM, will be examined.

What is SOM?
SOM, the System Object Model, is a language neutral object model. An Object in SOM is defined using an Interface Definition Language. The interface language is then "compiled" into a language specific form. For instance, if one were using C to implement the object, the SOM compiler would be used to produce .C, .IH, and .H files. The language specific form created by the SOM compiler has function stubs that the programmer would fill in. These stubs are the bodies to the member functions defined in the IDL. Because SOM objects can be used across different languages and compilers, they use the same linkage as OS/2's API and their names are not mangled like in C++.

OS/2 2.11 and previous versions of OS/2 2.x use SOM 1 in the Workplace Shell (WPS). SOM 1 is also central to the design of VX-REXX, and VisPro/REXX. (Of course, any WPS based application is also SOM based.) Not too worry, SOM 1 based applications will still run when SOM 2 is installed because SOM 2 is backwards compatible to SOM 1. The following list specifies some of the ways in which SOM 2 differs from SOM 1: Objects in SOM can be packaged in DLLs or in EXEs. Using DLLs offers the greatest flexibility. In fact, this is how one can extend the WPS and the other SOM based programs mentioned above.
 * 1) allows multiple inheritance
 * 2) allows derived metaclasses
 * 3) is CORBA compliant
 * 4) methods can return structures
 * 5) multiple classes can be packaged within a single file

DSOM

DSOM (Distributed System Object Model) allows SOM objects to be manipulated across processes. These processes can even be on different machines. In theory, this could make extending the WPS much easier than it presently is. If the WPS is written to use DSOM objects, then it will be possible to write WPS objects that can run in their own EXE and debug that EXE instead of the whole WPS.

Note: the WARP II beta ships with SOM 2.

The toolkit ships with a few goodies. The first item, called "Replication Frameworks", allows an object to exist in multiple processes at the same time, even across networks. Changes to any replicated object will be relayed to all replicas of the object. The network type and other details are abstracted from the programmer. Next is the "Persistence Frameworks"; it is used to stored objects on to disk. The "Event Management Frameworks" can be used to encapsulate event based activities, like the PM message loop.

Now that we have briefly looked at some of the features in the SOM toolkit, we'll move on to a quick look at the SOM OOP model.

SOM OOP vs C++ OPP
First, let's take a quick look at how the two OOP models differ. SOM uses a more runtime oriented OOP model. That is, the exact function that is being called, or the size of the object may not be known until the code is executed. Methods are called using one of the following schemes: The above list is ordered by decreasing execution speed. Offset resolution is similar to "virtual functions" used in C++. The name-lookup method allows a method whose name is not known until run-time to be called. The most flexible and time consuming resolution method uses the dispatch-function. This method allows methods to be called using application specific rules. As mentioned before, method names are not mangled like they are in C++; this is because, unlike C++, SOM does not allow operators to be overloaded.
 * 1) Offset resolution (default)
 * 2) Name-lookup resolution
 * 3) Dispatch-function resolution

Metaclasses

Coming from a C++ background, this is where things get confusing. In C++, the most fundamental object is a class. Class methods or data members were declared as "static" member of the class. This is not the case in SOM. Classes are instances of metaclasses, and objects are instances of classes. The metaclass contains all the class specific functions and data. Roughly speaking, a metaclass can contain data and methods that were either explicitly of implicitly defined as being static in C++.

Note: constructors are implicitly static member functions in C++.

A Simple Example
We'll take the "Hello World" example created by IBM and add some class data and methods to it. The source code presented here will have the IBM disclaimers stripped, if you really want to read them, see the source code files. We start by looking at HELLO.IDL. To the Hello class, I have added the member void sayHello. To the M_Hello metaclass, I have added the member attribute string ClassData. An attribute is merely a data member that has _get_ and _set_ methods automatically defined for it. The original code can be found in the \som\samples\somk\cpp\derived directory if the samples were installed with the toolkit. The code for sayHello is shown below. This code illustrates how to access instance data and class data. The code below is written using the C++ bindings. It is worth noting that the data/attributes are accessed by calling methods rather than by explicitly using the attributes name. Also, class data is accessed by using a pointer to an instance of the M_Hello metaclass.

Note: M_Hello is the metaclass for Hello.

Now lets put this code to work.

Wrapping Things Up
We briefly looked at some of the components of the SOMobjects Developers Toolkit. In addition a simple SOM 2 example was presented. In the next issue, we will look at creating a SOM class that encapsulates the INI interface.