The Run-time Library and VCL

The Run-time Library and VCL

Located in the source\rtl directory of the Delphi for .NET Preview installation, you will find the source files for the run-time library (RTL). You can already see the migration of units into CLR namespaces, as reflected in the source filenames.

Borland is taking the approach (for the most part) of preserving the original unit name and prefixing it with the namespace name Borland.Delphi. Operating system–specific things (such as registry and ini file utilities) go in the Borland.Win32 namespace, because these classes, procedures, and functions are Borland-specific wrappers of Windows-specific features. The naming trend should continue, although not all units will make the transition, and some will have their contents reorganized into an appropriate namespace.

Perusing the RTL source files is both highly educational and highly recommended; however, remember that you are looking at a preview release of a product, not the final version. The contents of the RTL source files are still subject to change—you should not make any assumptions, and you should definitely not introduce dependencies into your own code based on what you see there.

Class Helpers for the RTL

With the warnings out of the way, let's see what has been done to the RTL so far. The most interesting change is perhaps the introduction of class helpers.

Borland.Delphi.System.pas includes the following declaration:

  TObject = System.Object;

It tells you that Delphi's TObject class is an alias for the CLR class System.Object. This is important: TObject is not a descendant of System.Object—it is semantically equivalent. What happened to the methods that used to be defined in TObject, such as ClassName and ClassParent? That's where the class helper comes in.

The methods that used to be directly declared and implemented in TObject are now declared and implemented in a class called TObjectHelper. TObjectHelper is then declared to be a class helper for TObject. In Borland.Delphi.System.pas is the following:

  TObjectHelper = class helper for TObject
    procedure Free;
    function ClassType: TClass;
    class function ClassName: string;
    class function ClassNameIs(const Name: string): Boolean;
    class function ClassParent: TClass;
    class function ClassInfo: TObject;
    class function InheritsFrom(AClass: TClass): Boolean;
    class function MethodAddress(const Name: string): TObject;
    class function SystemType: System.Type;
    function FieldAddress(const Name: string): TObject;
    procedure Dispatch(var Message);

A class helper gives you a way to extend a class without using derivation.

You might want to extend a CLR class but not derive from it in order to use the CLR class with existing Delphi code. No doubt you've noticed that Delphi's class framework and the .NET Framework share a fair amount of functionality. In some cases there are name clashes between the two—for example, Borland's Exception class and the CLR's System.Exception class. On one hand, the two classes do basically the same thing, but they expose that functionality in different ways. On the other hand, large amounts of existing Delphi code have been using Borland's Exception class for a long time.

The only workable solution was to create a mechanism that would allow developers (including Borland) to leverage the CLR classes, and that would also allow the CLR classes to be extended to include long-standing behaviors expected by existing Delphi code.

Part I: Foundations