Delphi Clinic C++Builder Gate Training & Consultancy Delphi Notes Weblog Dr.Bob's Webshop
Dr.Bob's Delphi Notes Dr.Bob's Delphi Clinics Dr.Bob's Delphi Courseware Manuals
 Dr.Bob Examines... #6
See Also: other Dr.Bob Examines columns or Delphi articles

In this article (which was published in the DCon2000 edition of the UK-BUG NewsLetter), I'll write a wrapper around the CodeSite Debugging Object from Raize Software, in order to turn it into a Delphi 5 CORBA Server. Mr.Haki has already written a follow-up article in which he writes a JBuilder 3.5 CORBA Client (on Linux) that talks to this CodeSite CORBA Server.

Delphi 5 CORBA Server
I start by developing a CORBA Server which encapsulates some features of the CodeSite debugger from Raize Software. CodeSite is my debugger of choice, for both Delphi and C++Builder, and offers a CodeSite object (to link in with my Delphi and C++Builder applications) as well as a CodeSite viewer. The CodeSite object contains several methods to send information (strings, integers, etc.) to the viewer, which displays the messages in a useful way using indenting, timestamps, etc. For more information on CodeSite, check out the Raize Software website.
Start Delphi 5 with a new application, and add a CORBA Object to it (from the Multitier tab of the Object Repository):

When you select the CORBA Object icon and click on the OK-button, the "CORBA Object Wizard" is displayed. Here, we can specify what kind of CORBA Server we need. Apart from the name, which is set to CodeSite, we must specify a value for Instancing and the Threading Model. For "instancing", we can select Instance-per-client, which means that for each client connection, a new instance of the CORBA object is created.
The alternative is a shared-instance, which means that a single CORBA object is shared between each client. In this case, I've selected the Instance-per-client model. The threading model can be single-threaded or multi-threaded. In this case, I want to avoid all threading issues, so I've selected the single-threaded model:

After you've set all these options, click on OK to generate your CORBA object. The most important line in the source code (see below) can be found inside the initialization section, where the TCorbaObjectFactory.Create is called to create the CodeSiteFactory. Note that this is the place that specifies our choices for iMultiInstance (i.e. instance-per-client instead of shared-instance)and tmSingleThread. This also means that we can change these settings at a later time, for example change iMultiInstance to iSingleInstance to change our CORBA server to an instance-per-client object.

  unit CSServer;
  interface
  uses
    Windows, Messages, SysUtils, Classes, Graphics, Controls, ComObj, StdVcl,
    CorbaObj, CSCServer_TLB;

  type
    TCodeSite = class(TCorbaImplementation, ICodeSite)
    private
      { Private declarations }
    public
      { Public declarations }
    end;

  implementation
  uses
    CorbInit;

  initialization
    TCorbaObjectFactory.Create('CodeSiteFactory', 'CodeSite',
     'IDL:CSCServer/CodeSiteFactory:1.0', ICodeSite,
      TCodeSite, iMultiInstance, tmSingleThread);
  end.
Interfaces
First, add the RzCsIntf unit to the uses clause of the implementation section. This will make sure we have access to the (global) CodeSite object. The CodeSite object has over 20 methods that we can use to send information to the CodeSite Viewer window (which is shown on the same machine that executes the CodeSite CORBA Server). At this time, we don't want to expose all CodeSite methods to the outside world, so we'll focus on the most important ones. The SendMsg procedure can be used to send a string message to the viewer, which is the most commonly used CodeSite method.
There are numerous other SendXXX methods, but just about anything can be converted to a string in some way, so with the SendMsg method we cover a lot already. Apart from this method, there are two others that are special: EnterMethod and ExitMethod. These two can be used to display a string, but also to indent/unindent the output on the CodeSite viewer. Quite handy.
For now, these three methods: SendMsg, EnterMethod and ExitMethod are the interface we'd want to make available to the clients of our CORBA server. All three have a single string parameter. So, start the Type Library Editor and create three new methods (SendMsg, EnterMethod and ExitMethod) and give them all a single [in] string parameter. Note that we need to use BSTR when using the "IDL"-version of the Type Library, and WideString in the "Pascal"-version of the Type Library. You can change the versions on the Type Library tab of the Tools | Environment Options dialog.

Make sure to click on the "Refresh Implementation" button so the three methods are also reflected in the CSServer unit itself. At this time, we can export the IDL definition (click on the arrow-button on the upper-right of the Type Library Editor, and export the type library as CORBA IDL). The resulting IDL file can be seen below:

  module CSCServer
  {
    interface ICodeSite
    {
      void SendMsg(in wstring Str);
      void EnterMethod(in wstring Str);
      void ExitMethod(in wstring Str);
    };

    interface CodeSiteFactory
    {
      ICodeSite CreateInstance(in string InstanceName);
    };
  };
Once we have this CORBA IDL file, we can send it to the other side (in this case I've e-mailed it to Hubert to let him create a JBuilder 3.5 on Linux CORBA Client for it).

Server Skeleton
While Hubert is building his CORBA client based on our IDL file, we can go back to the CSServer unit to implement our server skeletons. For this, we actually need to use the CodeSite object itself, of course. Adding the RzCsIntf unit to the uses clause of our implementation section is enough, as this gives us access to the global CodeSite object.
Each of the three new methods of our CORBA server only need to call the CodeSite counterpart, passing the single WideString argument. CodeSite itself will take care of the rest.

  unit CSServer;
  interface
  uses
    Windows, Messages, SysUtils, Classes, Graphics, Controls, ComObj, StdVcl,
    CorbaObj, CSCServer_TLB;

  type
    TCodeSite = class(TCorbaImplementation, ICodeSite)
    protected
      procedure EnterMethod(const Str: WideString); safecall;
      procedure ExitMethod(const Str: WideString); safecall;
      procedure SendMsg(const Str: WideString); safecall;
    end;

  implementation
  uses
    CorbInit, RzCsIntf;

  procedure TCodeSite.EnterMethod(const Str: WideString);
  begin
    CodeSite.EnterMethod(Str)
  end;

  procedure TCodeSite.ExitMethod(const Str: WideString);
  begin
    CodeSite.ExitMethod(Str)
  end;

  procedure TCodeSite.SendMsg(const Str: WideString);
  begin
    CodeSite.SendMsg(Str)
  end;

  initialization
    TCorbaObjectFactory.Create('CodeSiteFactory', 'CodeSite',
     'IDL:CSCServer/CodeSiteFactory:1.0', ICodeSite,
      TCodeSite, iMultiInstance, tmSingleThread);
  end.
Each CORBA client that connects to this CodeSite CORBA server can use the EnterMethod, ExitMethod and SendMsg methods to send a debug message from the CORBA client to the CORBA server which will then display it inside the CodeSite Viewer that's running on the same machine. The output of Mr.Haki's JBuilder 3.5 on Linux CORBA Client is as follows:

The only problem, once we've got things working, is the fact that multiple CORBA clients can connect to our CORBA server at the same time. And while this doesn't mean we get threading issues, it does mean that we can't distinguish between messages from one client and another inside the CodeSite viewer: each message will be sent by... the CORBA server (since that's the application that's sending messages to CodeSite, not the CORBA client). A workaround would be to add the name of each CORBA client as first string to the three Str arguments. This can be done by the clients (not recommended) or by the Server automatically, provided we give each client a way to identify itself using an addition ID argument. We haven't implemented this feature in this article, but I'm sure you get the idea. For now, the result is that using a set of CORBA client stubs, we can write JBuilder applications on Linux and debug them on another machine running WinNT using CodeSite (provided the CodeSite CORBA server is running as well).


This webpage © 2000-2010 by Bob Swart (aka Dr.Bob - www.drbob42.com). All Rights Reserved.