Object oriented dynamic linking, late binding

System for object oriented dynamic linking based upon a catalog of registered function set or class identifiers

5615400

Abstract

A system is provided for managing code resources for use by client applications in a computer, wherein the computer has internal memory storing at least one client application. The apparatus comprises a resource set catalog stored in the internal memory. The resource set catalog identifies a plurality of function sets of functions by respective function set IDs. Further, the resource set catalog includes set records which characterize the functions within the respective sets. A dispatch engine, in the internal memory, linked with a client application, supplies a particular function set ID in response to a call by the client application of a particular function which is a member of a corresponding function set identified by the particular function set ID. A lookup engine in the internal memory, coupled with the resource set catalog and the dispatch engine, is responsive to the particular function set ID to look up a set record for a corresponding function set in the resource set catalog. Finally, a link engine in the internal memory and coupled with the dispatch engine returns the particular function to the client application in response to the set record. Thus, because the link engine is responsive to the set record, which is not linked with the client, the client need not be aware of changes in the structure of the library in which the particular function set resides. Thus, the function set can be moved into and out of internal memory, revised, placed in different sections of internal memory, and otherwise handled independently of the client, without requiring re-compilation of the client application.


Claims

What is claimed is:

1. A computer, comprising

a central processing unit;

non-volatile memory;

high-speed memory;

a library of function sets, each function set including at least one member function, embodied in the high-speed memory;

computer readable program code comprising one or more client applications embodied in the non-volatile memory and capable of utilizing and residing in the high-speed memory; and

computer readable program code means, embodied in the non-volatile memory, for managing use of functions by said one or more client applications, the computer readable program code means comprising:

computer readable program code means for causing the computer to store a dispatch record for said one or more client applications, each said dispatch record for said one or more client applications including a function set ID for each of said plurality of function sets used by said client application;

computer readable program dispatch code means responsive to a call by the client application of a particular member function and to the dispatch record for causing the computer to supply a request for a link to a function set having the particular member function; and

computer readable program link code means, responsive to the request for the link to the function set and to the function set ID in the dispatch record, for causing the computer to link the particular member function to the client application wherein the link code means includes

computer readable program code means for causing said computer to create a resource set catalog, the resource set catalog identifying function sets in the library by respective function set IDs, and storing a plurality of set records which characterize member functions within respective sets;

computer readable program lookup code means for causing the computer to look up a set record for the function set in the resource set catalog based on the corresponding function set ID; and

programmable code means, responsive to the set record, for causing the computer to return the particular member function to the client application.

2. The computer of claim 1, wherein the library of function sets includes at least one function set which characterizes a class.

3. The apparatus of claim 2, wherein the at least one function set which characterizes a class includes a constructor function and a destructor function.

4. The apparatus of claim 2, wherein the at least one function set which characterizes a class includes a virtual function.

5. The apparatus of claim 2, wherein the at least one function set which characterizes a class includes at least the following functions: a constructor function, a destructor function, a virtual function and a non-virtual function.

6. The computer of claim 1, wherein the computer readable dispatch code means includes:

a first level dispatch code segment linked to the client application and to a global variable in the high speed memory; and

a second level dispatch code segment linked to the global variable and the link code means.

7. The computer of claim 1, wherein the code means directing the computer to create a dispatch record includes code means causing the computer to create a function link cache with said dispatch record to store the function link to the particular member function;

the link code means further includes code means for causing the computer to supply the function link to the function link cache in response to the return of the particular member function to the client application; and

the dispatch code means further includes code means for causing the computer to query the function link cache for a cached link to the particular member function, and to jump to the particular member function in response to the cached link.

8. The computer of claim 1, wherein the dispatch record includes code means directing a set link cache to store a set link to the function set including the particular member function;

the link code means includes code means for causing the computer to supply the set link to the set link cache in response to the return of the particular member function to the client application; and

the dispatch code means includes a code means for causing the computer to query the set link cache for a cached link to the function set, and return the cached link to the link code means upon a call to a member function in the function set of the particular member function.

9. The computer of claim 8, wherein the function sets are assigned version numbers according to a standard protocol, and the dispatch record further includes version information linked with one of the client applications indicating a minimum version number supported by said one of the client applications for the function set of the particular member function;

the library includes a version number for the corresponding function sets; and

the link code means further includes code means, responsive to the version information in the dispatch record and the version number in the library, for ensuring that the client application supports a version of the function set of the particular member function.

10. The computer of claim 8, further including computer readable code means for causing the computer to load the function sets into high speed memory, to assign the function sets in the library serial numbers when the function sets are loaded in high speed memory, and to assign a serial number in the dispatch record, indicating the serial number corresponding to each function set when the set link cache is filled with set links,

the set link cache stores a pointer to a link structure in high speed memory, and the link structure includes a pointer for linking to the function set, and

the link code means further includes code means, responsive to the serial number in the library of the function set and the serial number in the dispatch record, for ensuring validity of the set link cache entry, and code means for clearing the link structure when the corresponding function set is unloaded from internal memory.

11. The computer of claim 8, wherein the library of function sets further includes use count records for function sets in the library and the link code means further includes code means for causing the computer to increment the use count record when the function set is returned to the client application, and to decrement the use count when the client application frees the function set.

12. The computer of claim 2, wherein the at least one function set which characterizes a class includes a constructor function and a destructor function and the library further includes use count records for function sets in the library;

the link code means further includes code means for directing the computer to increment the use count record for a particular function set when a client application calls a constructor function for a class characterized by the function set, and to decrement the use count record when a client application calls a destructor function for the class; and

further including programmable code means, responsive to the use count records in the library, for causing the computer to free corresponding function sets from internal memory when the use count record goes to zero.

13. The computer of claim 1, including programmable code means embodied in the non-volatile memory for causing the computer to create a plurality of link structures in high-speed memory, and wherein a subset of the function sets are stored in non-volatile memory and may be loaded into high-speed memory by the link code means, the link code means causing the computer to assign serial numbers to the function sets when loaded in high-speed memory;

the dispatch record further includes a set link cache to store a pointer to one of the plurality of link structures and to store a serial number indicating a serial number of the corresponding function set when the set link cache is filled;

the link structure includes a pointer for linking to the function set;

the link code means further includes code means for causing the computer to supply the link to the function set, to return a particular member function to the client application, and to supply the serial number to the set link cache in response to the return of the particular member function to the client application; and

the dispatch code means further includes programmable code means for causing the computer to query the set link cache for a cached link, and if the serial number in the set link cache matches the serial number in the library, to return the cached link to the link code means upon a call to a member function in the function set of the particular member function.

14. The computer of claim 1, wherein the link code means includes:

means for causing the computer to create a catalog in the internal memory which lists function sets available for linking; and

programmable registration code means, in the high-speed memory, for causing the computer to insert function sets in the library in the catalog in response to a request by an operating system to make the library available for linking, and to remove the function sets in the library from the catalog in response to a request by the operating system to make the library unavailable for linking.

15. The computer of claim 1, wherein the link code means includes:

means for causing the computer to create a catalog in the internal memory which lists function sets available for linking; and

programmable registration code means, executable during runtime of the client application and in the high-speed memory, for causing the computer to insert function sets in the library in the catalog in response to a request by an operating system to make the library available for linking, and removes the function sets in the library from the catalog in response to a request by the operating system to make the library unavailable for linking.

16. A computer, comprising:

an input;

a central processing unit;

non-volatile memory;

internal memory;

at least one client application embodied in internal memory; and

programmable code means for managing code resources for use by client applications in the computer, the programmable code means, comprising:

a resource set catalog stored in the internal memory, the resource set catalog identifying a plurality of function sets of member functions by respective function set IDs, and storing a plurality of set records which characterize member functions within respective sets;

dispatch code means, in the internal memory linked with a client application, for causing the computer to supply a particular function set ID in response to a call by a client application of a particular member function which is a member of the a function set identified by the particular function set ID in the resource set catalog;

lookup code means, in the internal memory, for causing the computer to identify, based upon the resource set catalog and responsive to the dispatch code means, one of said plurality of set records for the corresponding function set in the resource set catalog; and

link code means, in the internal memory and responsive to the dispatch code means, for causing the computer to return the particular member function to the client application in response to the set record.

17. The computer of claim 16, wherein the dispatch code means comprises:

a dispatch record, linked with the client application, which stores the particular function set ID; and

dispatch linked to the dispatch record and the lookup engine, responsive to the call to supply the particular function set ID to the lookup engine.

18. The computer of claim 17, wherein the dispatch record includes a set link cache to store a link to the set record for the set of functions including the particular member function;

the link code means further includes code means for causing the computer to supply the link to the set link cache in response to the return of the particular member function to the client; and

the dispatch code means further includes code means for causing the computer to query the set link cache for a stored link to the set record, and to return the set record to the link engine in response to the cached link upon a call to a member function in the function set of the particular member function.

19. The computer of claim 18, wherein the set records for function sets are assigned serial numbers when the function sets are loaded in internal memory, and the dispatch record further includes a serial number, linked with the client, indicating a serial number of the corresponding function set when the set link cache is filled;

wherein the set link cache stores a pointer to a link structure in internal memory, and the link structure includes a pointer to the set record having the particular function set ID of the set record, and

wherein the link code means further includes code means, responsive to the serial number in the set record and the serial number in the dispatch record, for causing the computer to insure validity of the set link cache entry, and to clear the link structure when the corresponding function set is unloaded.

20. The computer of claim 17, wherein the set record further includes a use count record and the link code means further includes code means for causing the computer to increment the use count when a client application binds with the function set corresponding to the set record, and to decrement the use count when a client application frees the function set corresponding to the set record.

21. The computer of claim 18, wherein the at least one function set which characterizes a class includes a constructor function and a destructor function, and the set record further includes a use count field;

wherein the link code means further includes code means for causing the computer to increment the use count when a client application calls a constructor function for a class corresponding to the set record, and to decrement the use count when a client application calls a destructor function for a class corresponding to the set record; and

further including code means, responsive to the use counts in the set records, for causing the computer to free corresponding function sets from internal memory when the use count goes to zero.

22. The computer of claim 20, including a plurality of link structures in internal memory, and wherein the function sets are loaded into internal memory and are assigned serial numbers when loaded in internal memory;

the dispatch record includes a set link cache to store a pointer to one of the plurality of link structures and to store a serial number indicating a serial number of a corresponding function set when the set link cache is filled;

the link structure includes a pointer to the set record; and

the link code means further includes code means for causing to computer to supply the link and the serial number to the set link cache in response to the return of the particular function to the client;

the dispatch code means further includes code means for causing the computer to query the set link cache for a stored link to the set record, and, if the serial number in the set link cache matches the serial number in the set record, to return the set record to the link engine in response to the cached link upon a call to a member function in the function set of the particular member function.

23. The computer of claim 16, further including:

registration code means in the internal memory for causing the computer to insert a library of function sets in the resource set catalog in response to a request to make the library available for linking, and to remove the function sets in the library from the resource catalog in response to a request to make the library unavailable for linking.

24. The computer of claim 16, further including:

registration code means, executable during runtime of the client application and in the internal memory, for causing the computer to insert a library of function sets in the resource set catalog in response to a request to make the library available for linking, and to remove the function sets in the library from the resource set catalog in response to a request to make the library unavailable for linking.

25. An article of manufacture, comprising:

a computer usable medium having computer readable program code means embodied therein for managing code resources used by client applications in a computer, said program code means comprising:

code resources comprising a library of function sets stored on the computer usable medium, the function sets in the library having function set IDs, and the function sets including member functions;

program code means for causing the computer to create a resource set catalog, the resource set catalog identifying function sets in the library by respective function set IDs, and to store a plurality of set records which characterize member functions within respective sets;

dispatch code means, linked with a client application, for causing the computer to supply a particular function set ID in response to a call by the client application of a particular member function which is a member of a corresponding function set identified by the particular function set ID;

program lookup code means, responsive to the particular function set ID, for causing the computer to query the resource set catalog to look up a set record for the corresponding function set in the resource set catalog; and

program link code means, for causing the computer to return the particular member function from the library to the client application in response to the set record, and to write valid links in the function link cache and the set link cache,

wherein the dispatch code means includes:

a dispatch record linked with the client application which stores the particular function set ID,

a function link cache, linked with the client application, to store a link to the particular member function,

a set link cache, linked with the client application to store a link to the set record for the set of functions including the particular member function,

a dispatch code means linked to the dispatch record, the function link cache, the set link cache and the lookup engine, responsive to the call to supply the particular member function if the function link cache is valid, for causing the computer to supply the set record if the set link cache is valid and to supply the particular function set ID if neither the function link cache nor set link cache is valid.

26. The article of manufacture of claim 25, wherein the library comprises at least one function set which characterizes a class.

27. The article of manufacture of claim 26, wherein the at least one function set which characterizes a class includes a constructor function and a destructor function.

28. The article of manufacture of claim 26, wherein the at least one function set which characterizes a class includes a virtual function in the class.

29. The article of manufacture of claim 26, wherein the at least one function set which characterizes a class includes a constructor function, a destructor function, a virtual function and a non-virtual function.

30. The article of manufacture of claim 25, wherein the function sets in the library are assigned version numbers according to a standard protocol, and dispatch record further includes version information linked with the client indicating a minimum version number supported by the client for the function set of which the particular function is a member,

the set record includes a version number for the corresponding function set, and

the link code means includes means, responsive to the version information in the dispatch record and the version number in the set record, for causing the computer to insure that the client supports a version of the particular function in the function set.

31. The article of manufacture of claim 25, wherein the set records for function sets are assigned serial numbers when the function sets are loaded in internal memory, and the dispatch record further includes a serial number linked with the client indicating a serial number of the corresponding function set when the set link cache is filled,

the set link cache stores a pointer to a link structure in internal memory, and the link structure includes a pointer to the set record having the particular function set ID of the set record, and

the link code means further includes means, responsive to the serial number in the set record and the serial number in the dispatch record, for causing the computer to insure validity of the set link cache entry, and means for clearing the link structure when the corresponding function set is unloaded.

32. The article of manufacture of claim 25, wherein the set record includes a use count record and the link means includes means for causing the computer to increment the use count when a client application binds with the function set corresponding to the set record, and to decrement the use count when a client application frees the function set corresponding to the set record.

33. The article of manufacture of claim 26, wherein the at least one function set which characterizes a class includes a constructor function and a destructor function and the set record further includes a use count field;

the link means includes means for causing the computer to increment the use count when a client application calls a constructor function for a class corresponding to the set record, and to decrement the use count when a client application calls a destructor function for a class corresponding to the set record; and

further including means, responsive to the use counts in the set records, to free corresponding function sets from internal memory when the use count goes to zero.

34. The article of manufacture of claim 25, including a plurality of link structures in internal memory, and wherein the function sets are assigned serial numbers when loaded in internal memory;

the set link cache stores a pointer to one of the plurality of link structures and a serial number indicating a serial number of the corresponding function set when the set link cache is filled;

the link structure includes a pointer to the set record; and

the link means includes means causing the computer to supply the link and the serial number to the set link cache in response to the return of the particular member function to the client;

the dispatch means includes means to insure the validity of a cached link to the set record in response to the serial number in the set link cache and the serial number in the set record.

35. The article of manufacture of claim 25, further including:

a registration routine in the memory which inserts a library of function sets in the resource set catalog in response to a request to make the library available for linking, and removes the function sets in the library from the resource catalog in response to a request to make the library unavailable for linking.

36. The article of manufacture of claim 25, further including:

a registration routine executable during runtime of the client application and in the memory, which inserts a library of function sets in the resource set catalog in response to a request to make the library available for linking, and removes the function sets in the library from the resource set catalog in response to a request to make the library unavailable for linking.

37. In a computer, a computer readable memory having code means for managing functions for use by client applications in the computer, the computer having internal memory storing at least one client application and non-volatile memory, the code means comprising:

a resource catalog stored in the internal memory, the resource catalog including records identifying a plurality of functions available for dynamic linking with the client application;

dispatch code, in the internal memory linked with a client application, causing the computer to supply a request to link with a particular function in response to a call by the client application of the particular function;

lookup code in the internal memory, coupled with the resource catalog and the dispatch engine, causing the computer to look up a record for the particular function in the resource catalog in response to the request;

link code, in the internal memory and coupled with the dispatch engine, causing the computer to return the particular function to the client application in response to the record; and

registration code in the internal memory executable during runtime of the client application, which the inserts records for a library of functions in the resource catalog in response to a request to make the library available for linking, and removes the records for the library from the resource catalog in response to a request to make the library unavailable for linking.

38. A computer, including at least one central processing unit, non-volatile memory, high-speed memory, code means for managing code resources for use by client applications, the volatile memory storing at least one client application, the code means comprising:

a class catalog stored in the internal memory, the class catalog identifying a plurality of classes by respective class IDs, and storing class records which characterize derived classes, each derived class having at least one corresponding class in the plurality of classes from which the derived class is derived;

dispatch code in the internal memory linked with a client application, to supply a particular class ID in response to a call by the client application of a function of a particular class identified by the particular class ID;

lookup code in the internal memory, coupled with the class catalog and the dispatch engine, responsive to the particular class ID, causing the computer to look up a class record for the corresponding class in the class catalog;

link code in the internal memory and coupled with the dispatch engine, causing the computer to return the function of the particular class to the client application in response to the class record; and

library management code, coupled with the class catalog, causing the computer to provide information about a class in the class catalog to the client application in response to the class ID.

39. The computer of claim 38, wherein the class records identify classes from which the corresponding class is derived, and the library manager includes a verify class routine to verify that a particular class is derived from another class.

40. The computer of claim 38, wherein the class records identify parent classes of the corresponding class, and the library manager includes a cast object routine to return offsets within an object of a particular class to elements within the object of a parent class of the particular class.

41. The computer of claim 38, wherein the library manager includes a new object routine to provide parameters to the client application for calling a function of a class in response to the class ID.

42. The computer of claim 38, wherein the library manager includes a get class information routine to provide information to the client application about classes derived from a particular class in response to the class ID of the particular class.

43. A process for managing code resources used by a client application in a computer and dynamically installing client applications, the computer having internal memory storing at least one said client application, comprising:

providing a class identifier and link pointer in the client application;

providing a class catalog in the internal memory, the class catalog identifying a plurality of classes by respective class identifiers;

providing class records which contain information regarding each class and table records which characterize corresponding classes; and

updating the class catalog by generating a new object for inclusion in the class catalog, wherein said generating comprises means for:

querying the class identifier;

querying a memory pool;

determining, based on the class identified and memory allocation data, whether the memory pool allocation has been allocated to an object;

if the memory location has not been allocated, allocating the memory pool location to the new object;

determining the class record by querying one of the plurality of classes to determine whether the new object is supported by the class;

if the class is associated with a library other than a root library, then loading the library and incrementing a use counter in the table record;

retrieving the table record using the class record;

determining whether the new object is supported by the class based on the table record;

determining the size of the new object based on the object record;

placing the object in the allocated memory pool; and

incrementing the use counter.

44. A process executable in a computer, the computer including client applications in the computer, comprising the steps of:

providing a class identifier and link pointer in the client application;

providing a class catalog, the catalog stored in the internal memory, the class catalog identifying a plurality of classes by respective class identifiers, and storing class records which characterize corresponding classes, including at least one parent class having at least one class, each class comprising at least one object;

providing at least one operating system designated folder holding a register library;

determining whether new files are copied to or removed from the folder by the client application; and

updating the class catalog to include new library resources copied into the folder and deleting library resources which have been moved from the folder subsequent to use.

45. The process of claim 44 wherein the step of providing further includes the step of providing at least one client application designated folder.

46. The process of claim 45 wherein the step of determining further includes intercepting operating system calls indicating whether a file has been copied or moved, and means for determining whether the file is located in the operating system designated folder or the client application designated folder.

47. The process of claim 45 further including the step of determining whether the new file is a shared library resource prior to the step of updating the class catalog.

48. A computer readable memory for managing code resources for use by client applications in a computer, the computer having internal memory storing at least one client application, comprising:

a class catalog stored in the internal memory, the class catalog identifying a plurality of classes by respective class identifiers, and storing class records which characterize corresponding classes;

link code means, in the internal memory, for causing the computer to return the particular function to the client application in response to the class record;

library management code means, coupled with the class catalog, causing the computer to provide information about a class in the class catalog to the client application in response to a request to make the library unavailable for linking; and

a registration code means causing the computer to insert a library of function sets in the class catalog in response to a request to make the library available for linking, and to remove the function sets in the library from the class catalog in response to a request to make the library unavailable for linking.

49. The system of claim 48 further including:

cast object code means coupled to the client applications, allowing the client to cast an object of as a parent class, the cast object routine comprising:

code means for determining the location of the object and an identifier of the parent class;

code means for determining the class of the object based on a required structure for the object;

code means for verifying the class of the object using the class identification of the object and the parent class identifier;

code means for determining whether a single or multiple inheritance of the class is found; and

code means for determining offsets necessary for multiply inherent objects based on a hierarchy of parent classes.

50. The system of claim 48, wherein the catalogs are assigned version numbers according to a standard protocol, and including version information linked with the client application indicating a minimum version number supported by the client application for the function set of the particular member function,

the library includes a version number for the corresponding function sets, and

the link code further includes code, responsive to the version information in the dispatch record and the version number in the library, for causing the computer to insure that the client application supports a version of the function set of the particular member function.

51. A computer including internal memory storing at least one client application and non-volatile memory storing programmable code, the code comprising:

a class identifier and link pointer in the client application, upon compiling the client application;

a class catalog, the catalog stored in the internal memory, the class catalog identifying a plurality of classes by respective class identifiers, and storing class records which characterize corresponding classes, including at least one parent class including at least one class, each class comprising at least one object;

at least one operating system designated folder holding a register library;

means for determining whether new files are copied to or removed from the folder by the client application; and

update code means for including new library resources copied into the folder in the class catalog and deleting library resources which have been moved from the folder subsequent to use from the class catalog.

52. A computer including a central processing unit, volatile internal memory and non-volatile memory means for managing code resources for use by client applications in the computer, the computer having internal memory storing at least one client application, said means for managing code comprising:

means for providing a class identifier and link pointer in the client application;

means for providing a class catalog stored in the internal memory, the class catalog identifying a plurality of classes by respective class identifiers, and storing class records which characterize corresponding classes, including at least one parent class having at least one class, each class comprising at least one object;

means for providing at least one operating system designated folder and at least one client application designated folder, each holding at least one register library;

means for determining whether new files are copied to or removed from the folder by the client application;

means for determining whether the new file is a shared library resource; and

means for updating the class catalog to include new library resources copied into the folder and deleting library resources which have been moved from the folder subsequent to use.


Description

LIMITED COPYRIGHT WAIVER

A portion of the disclosure of this patent document contains material to which the claim of copyright protection is made. The copyright owner has no objection to the facsimile reproduction by any person of the patent document or the patent disclosure, as it appears in the U.S. Patent and Trademark Office file or records, but reserves all other rights whatsoever.

BACKGROUND OF THE INVENTION

1. Field of the Invention

The present invention relates to dynamic linking of client applications with function sets or classes used by the client applications; and, more particularly, to systems for dynamically linking a client application at run time with libraries of function sets or classes registered either before or during execution of the client application.

2. Description of the Related Art

Traditionally, an application's source files are compiled in object modules and then linked together with other object modules, generically called libraries, to form a complete stand-alone application. This is called static linking. A disadvantage of static linking is that each application that links with the same library routine has its own private copy of the routine. Most of the size of the applications comes from the library code linked to each application. Another disadvantage of static linking is that the functionality that the application gets from the library is fixed. If the library has a bug in it, the application has to be re-linked with the new library to get the bug fixed.

Dynamic linking, sometimes called late binding, differs because the application code and library code are not brought together until after the application is launched. If the code in the library is not loaded until it is actually required, then this is called dynamic loading.

If the same copy of library code being used by one application can be used by other applications at the same time, then the library is called a shared library.

Dynamic linking of a class or function set involves binding code ("client application") which uses a class or function set to the code which implements the class or function set at run time. Thus, the term "dynamic" in this context, means "occurring at run time". Linking entails both loading the code and binding imported references to exported implementations of the classes or function sets. Existing dynamic linking systems do not provide class level or function set level dynamic linking. Instead, the linking is done at the level of the individual functions which may be exported by a library and imported by a client. However, each individual function must be exported by the library and each function used by the client must be imported in such prior art systems. To complicate matters, the name of the functions after compilation is not the name of the same in the source code (i.e., C++). Thus, the developer must deal with so-called "mangled" names to satisfy parameters of the dynamic linking systems of the prior art.

Among other limitations, prior individual function level binding systems cause the implementation of a client to be dependent on a particular set of classes known at build time. Thus, new derived classes cannot be added later without having to rebuild the client. Further, prior art dynamic linking systems do not provide for dynamic installation of the linking system itself. In some cases, after a new linking system is installed, the host system must be rebooted or at least the client application has to be restarted.

Existing dynamic linking systems are designed to support procedural programming languages and do not provide object oriented dynamic linking. Since some object oriented languages are derivatives of procedural languages (e.g., C++ is a derivative of C) these systems can sometimes provide dynamic linking of an object oriented language, provided the programmer deals with a class by the awkward approach of explicitly naming all members of the class. Nonetheless, these systems do not directly support object oriented programming languages.

Accordingly, it is desirable to optimize a dynamic linking system to object oriented programming systems involving class level or function set level dynamic binding. Furthermore, such system should be robust, supporting efficient use of internal memory, and versioning of function sets or classes. Finally, it is desirable to provide for dynamic registration of updated or new libraries, so that a client application need not be restarted in order to take advantage of new versions of its libraries.

SUMMARY OF THE INVENTION

The present invention provides explicit support for object oriented languages, such as C++, MCL, and Dylan. This support includes linking by class or class identifier where a library exports a class and a client imports a class. The client has access to all of the public virtual and non-virtual member functions of such dynamically linked classes. Also, the client may instantiate an object of a class which was not known at compile time. In this case, the client can call public virtual member functions using a known interface of one of the parent classes of a class.

The system of the present invention employs a dynamic function set catalog which can be queried directly or indirectly by the client. Since, ultimately, the implementation of a class is a set of functions, it is possible to dynamically link classes. The dynamic function set or class catalog is updated from a catalog resource when a library is registered and when a library is unregistered with the system. Each registered function set or class is given an identifier when registered.

The system is particularly suited to object oriented programming environments, where for a function set which characterizes a class; a direct catalog query by a client can determine for a given identifier, and the corresponding information in the catalog (1) whether the class is available, (2) the class IDs of its parent classes, (3) the class IDs of its derived classes, and (4) whether the class can be dynamically instantiated by a class ID. These functions enable clients to dynamically determine the availability and compatibility of classes, and enable new functionality to be delivered in the form of new shared class libraries and added to a client without recompiling the client. Since all code that implements a class can be dynamically linked, the client is not dependent on the implementation of the library code. A library can be fixed or enhanced without having to rebuild the client or other libraries. This simplifies the development and distribution of fixes and enhancements, and is generally better than existing patching mechanisms. Since other dynamic linking systems are not aware of classes as a distinct entity, the concept of class identification and class catalog management does not exist in these systems.

Accordingly, the present invention can be characterized as a system for managing code resources for use by client applications in a computer, wherein the computer has internal memory storing at least one client application. The apparatus comprises a resource set catalog stored in the internal memory. The resource set catalog identifies a plurality of function sets by respective function set IDs. Further, the resource set catalog includes set records which characterize the implementation of functions within the respective sets.

A dispatch engine, in the internal memory, linked with a client application, supplies a particular function set ID in response to a call by the client application of a particular function which is a member of a function set identified by the particular function set ID. A lookup engine in the internal memory, coupled with the resource set catalog and the dispatch engine, is responsive to the particular function set ID to look up a set record for a corresponding function set in the resource set catalog. Finally, a link engine in the internal memory and coupled with the dispatch engine returns the particular function to the client application in response to the set record. Thus, because the link engine is responsive to the set record, which is not linked with the client, the client need not be aware of changes in the structure of the library in which the particular function set resides. Thus, the function set can be moved into and out of internal memory, revised, placed in different sections of internal memory, and otherwise handled independently of the client, without requiring re-compilation of the client application.

The resource set catalog is characterized as containing set records for function sets, where a class for an object oriented system is a type of function set. Thus, where the term "function set" is used in the claims, it is intended that a species of function set may be a class.

According to one aspect of the invention, the dispatch engine includes a dispatch record which is linked with the client, and stores a particular function set ID corresponding to a function set of which the called function is a member. Also, a dispatch routine is included in the dispatch engine, which is linked to the dispatch record and the lookup engine, and responsive to the call to the particular function to supply the particular function set ID to the lookup engine. In one preferred embodiment, the dispatch routine includes a first level dispatch segment linked to the client and to a global variable in the internal memory, and a second level dispatch segment linked to the global variable and the lookup engine.

According to yet another aspect of the present invention, the dispatch record includes a function link cache and a set link cache. The function link cache stores a link to the particular function which is supplied by the link engine in response to the return of the particular function to the client. The dispatch engine includes a routine which looks at the function link cache for a cached link to the particular function and jumps to the particular function in response to the cached link if present.

The set link cache stores a link to the set record for the set of functions including the particular function which had been previously called by the client. The link engine includes a routine that supplies the link to the set link cache in response to return of a particular function to the client. The dispatch engine includes a routine which looks in the set link cache for a cached link to the set record, and returns the set record to the link engine in response to the cached link upon a call to a function which is a member of the function set.

Thus, a function call can be executed quickly if the function link cache is full, with a medium level of speed if the set link cache is full, and more slowly if a catalog search is needed to bind the function implementation.

The invention further provides for assignment of version numbers to function sets according to a standard protocol. The dispatch record in this aspect includes version information linked with the client indicating a minimum version number supported by the client for the function set of which the particular function is a member. The set record includes a version number for the corresponding function set. The link engine in this aspect includes a routine which is responsive to the version information in the dispatch record and the version number in the set record to insure that the client supports a version of the particular function in the function set.

In addition, the function sets are assigned serial numbers when loaded in internal memory. The dispatch record further includes a serial number linked with the client indicating a serial number of the corresponding function set when the set link cache is filled. The set link cache stores a pointer to a link structure in internal memory and the link structure includes a pointer to the set record having the particular function set ID. The set record stores the assigned serial number for the function set when it is loaded in internal memory. The link engine includes a routine responsive to the serial number in the set record, and the serial number in the dispatch record to insure validity of the set link cache entry, and a routine for clearing the link structure when the corresponding function set is loaded.

The invention further provides for a use count record within the set record. The link engine in this aspect includes a routine to increment the use count when a client application binds with the function set corresponding to the set record, and to decrement the use count when a client application frees the function set corresponding to the set record. When the function set characterizes a class, the use count is incremented when a constructor for the class is called, and decremented when a destructor for the class is called. Thus, using the use count, the memory management system can unload function sets which are not in current use by any active applications.

Since a client can enumerate all derived classes of a given class by class ID, it can determine what classes are available dynamically. The set of available classes can be extended at run time when new libraries are registered and a client can instantiate a class even though it is added to the system after the client was launched. New classes can be copied into a library directory or folder in the file system at any time and are automatically registered, or a new folder or file can be explicitly registered as a library container by a client.

Dynamic registration of libraries of function sets or classes is accomplished using the class catalog. Because the class catalog is not bound with clients, all that needs to be done to register a new library, is to write the appropriate records into the class catalog. Once the appropriate records are written into the class catalog, the new library becomes available to the new client. The procedures outlined above are in place to protect the client from using a version of a class or function set which it does not support, and for finding an unloaded and reloaded version of a particular function which it has already used.

The invention further provides for insuring type safety of the dynamically linked classes and function sets by means of shared library functions specifically designed to take advantage of the class catalog to insure such safety. The particular functions include the new object function, by which a client application may obtain information needed to construct a new object using the shared library manager, with reference to the class ID of the new object. Thus, using a class ID, the library manager looks up the information about the class in the class catalog, and returns a constructor for the class to the client. The client is then able to call the constructor, even if it did not know at the time it was written or compiled about the class.

In addition, the library manager provides a verify class routine, by which a client application may verify the parent of a particular derived class for type safety. Finally, a cast object routine is provided, by which a client may cast an instance of a particular object as a parent class object. This routine utilizes the class catalog to return offsets within the particular object to the elements of the parent, even though the client application may not have been aware of the structure of the parent at the time it was written or compiled.

Accordingly, it can be seen that the present invention provides a dynamic class catalog which given a class ID can be queried to determine whether the class is available, the class IDs of the parent class or classes, the class ID or IDs of the derived class or classes, and whether the class can be dynamically instantiated by class ID. When an object is instantiated, the library or libraries which implement the class and its parent classes are dynamically loaded. An object can be instantiated by a client which had no knowledge at compile time of the class of the object. If such client was compiled with the interface of a parent class of the object, then the object can be used as if it were an instance of the parent class.

The system is particularly suited for object oriented dynamic linking which enables dynamic library registration, dynamic inheritance, and on-demand type-safe dynamic instantiation of objects by class identifier.

Other aspects and advantages of the present invention can be seen upon review of the figures, the detailed description, and the claims which follow.

BRIEF DESCRIPTION OF THE FIGURES

FIG. 1 is a schematic diagram of a computer system implementing the shared library manager of the present invention.

FIG. 2 is a schematic diagram of the resource set catalog used according to the present invention.

FIG. 3 is a diagram of the data structures involved in the dynamic binding of the present invention.

FIGS. 4A-4C provide the "C" language definition of the stub record, client VTable record and class VTable records according to a preferred embodiment.

FIGS. 5A and 5B provide a flowchart for the basic dispatching architecture used with the shared library manager of the present invention.

FIGS. 6A, 6B, and 6C provide a flowchart for the GET CLASS VTABLE RECORD step 112 of FIG. 5B.

FIG. 7 is a schematic diagram of the library registration function, and organization.

FIG. 8 is a flowchart illustrating the operation of the dynamic registration routine using the structure of FIG. 7.

FIGS. 9A and 9B illustrate a new object routine executed by the shared library manager.

FIG. 10 illustrates a variant of the new object routine used when type safety is desired to be verified.

FIG. 11 is a flowchart for a verify class routine executed by the shared library manager.

FIG. 12 is a flowchart for a cast object routine executed by the shared library manager.

FIG. 13 is a flowchart for a GetClassInfo routine executed by the shared library manager.

DESCRIPTION OF THE PREFERRED EMBODIMENTS

A detailed description of preferred embodiments of the present invention is provided with respect to the figures. FIGS. 1-13 provide a high level overview of enabling various aspects of the present invention. A detailed description with references to segments of the source code follows a description of the figures.

FIG. 1 shows a computer system in which the present invention is loaded. The computer system includes a host CPU 10 which includes a plurality of registers 11 used during execution of programs. The CPU is coupled to a bus 12. The bus communicates with an input device 13 and a display 14 in the typical computer system. Further, non-volatile memory 15 is coupled to the bus 12. The non-volatile memory holds large volumes of data and programs, such as libraries, client applications, and the like. A high speed memory 16 is coupled to the bus 12 for both data and instructions. The high speed memory will store at least one client application 17, a shared library manager 18, shared library manager global variables at a predetermined address space within the memory 16, exported libraries 20, and other information as known in the art.

According to the present invention, when a client application is compiled, a number of items are provided within the application. These items include a stub record, stub code, a library manager interface, a client VTable record, and a first level dispatch routine. The shared library manager will include a library builder routine, a resource set catalog, a second level dispatch routine, class VTable records for registered libraries, a lookup function, and a link function.

As mentioned above, the resource set catalog provides information for function sets or classes which are available to a client. The stub record points to the client VTable record within the client. The first level dispatch routine uses information in the client VTable record to call the second level dispatch routine. The second level dispatch routine calls the lookup function to find information about the called function in the resource set catalog. That information is provided to a link engine in the form of a class VTable record which links the client to the particular function that it has called. A particular protocol for using these features of the client and the shared library manager are described below with reference to FIGS. 5 and 6.

The implementation of the resource set catalog, also called a class catalog herein, is shown in FIG. 2. A class catalog is a record 30 which includes a first field 31 which stores a number indicating the number of exported classes in all the library files which have been registered with the catalog 30. Next, the catalog includes an array 32 which stores class information records, one per exported class. The class information record in the array 32 consists of a structure 33 which includes a number of parameters. This structure includes a first field 34 named library which points to the library in charge of the code for the particular class or function set. A second field 35 stores a class serial number which is unique for each instance of the class; that is, it is incremented on registration of the class.

A next field 36 stores a VTable record pointer which is the pointer to the VTable record for this class. A next field 37 stores a class ID, which is a class identifier for the class. A next record 38 stores the parent class ID. This is the class ID for a parent of this class. Next, a plurality of flags are stored in field 39 which are defined in more detail below. A next field 40 is a class link pointer. This points to a link structure for establishing a link with the client VTable record. Field 41 stores a version parameter indicating a version of the class implementation.

The class information record is loaded from a library resource having a structure described below with reference to FIG. 8.

FIG. 3 schematically illustrates the records used for dynamically linking a function call in a client to a class or function set. The figure is divided generally along line 50. Where elements above line 50 are linked with the client during compile time, and elements below line 50 are linked with the shared library manager. Thus, the client includes a stub record 51 which provides a function link cache for a pointer to the implementation of the called function, and a pointer 52 to a client VTable record 53. The client VTable record stores the class identifier, for the class or function set, and a class link pointer providing a set link cache. The class link pointer 54 points to a link structure 55 which stores a pointer 56 to a class information record 57 in the class catalog. The class information record includes a pointer 58 to the class VTable record 59. The class VTable record includes a pointer 60 to the actual VTable of the class, and a pointer 61 to an export table for non-virtual functions.

If the class link pointer 54 is null, then a lookup function is called which accesses the class catalog 62 to look up the class information record 57 for the corresponding function. If that function is registered, then the class information record 57 is supplied, and the class VTable record 59 may be retrieved.

The figure also includes a schematic representation of a load engine 64. The load engine is coupled with the class information record 57. If the class corresponding to the class information record is not loaded at the time it is called, then the load engine 64 is invoked. When the information is moved out of longterm storage into the high speed internal memory, the class information record 57 and class VTable record 59 are updated with the correct pointers and values.

FIGS. 4A, 4B, and 4C respectively illustrate the actual "C" definitions for the stub record, client VTable record, and class VTable record according to the preferred implementation of the present invention. Details of these structures are provided below in the description of a preferred embodiment. They are placed in these figures for ease of reference, and to illustrate certain features. It can be seen that the client VTable record (FIG. 4B) includes version information (fVersion, fMinVersion) which indicates a current version for the function set or class to which the class link pointer is linked, and the serial number (fClassSerialNumber) for the same. The class information record 57 of FIG. 3 also includes version information for the currently loaded class for a function set, and the serial number for the currently loaded class or function set. These fields are used for insuring version compatibility between the client and the currently loaded library, as well as validity of the link information.

The class VTable record 59 (FIG. 4C) also includes a use count parameter (fUseCount). The use count parameter is incremented each time a class is constructed, and decremented each time a class is destructed. When the use count returns to zero, the class or function set is freed from internal memory.

FIGS. 5A and 5B provide a flowchart for the basic implementation of the run time architecture. The algorithm begins by a client application calling a class constructor or a function by name (block 100). The stub code, generally outlined by dotted line 90, in the client with a matching name refers to the linked stub record (block 101). The stub code then tests whether the stub record includes the address for the constructor or function in its function link cache (block 102). If it does, then the stub code jumps to the address (block 103). This is the fastest way in which a function may be executed.

If the stub record did not include a valid cached address for the function, then the stub code calls a first level dispatch routine (block 104).

The first level dispatch routine is generally outlined by dotted line 91. The first step in this routine is to load a pointer to the library manager interface in the client in a host register (block 105). Next, the offset to the second level dispatch routine is read from the SLM global variables in internal memory (block 106). Next, the second level dispatch routine is jumped to based on the offset read in block 106 (block 107).

The second level dispatch routine is generally outlined by dotted line 92. The second level dispatch routine begins by pushing pointers for the client library manager interface and stub record onto the stack (block 108). Next, a lookup function is called for the class catalog (block 109).

The lookup function is generally outlined by dotted line 93. The first step in the lookup function is to take the stub record and library manager interface for the client (block 110). Using the information, the lookup function retrieves the class identifier for the named class or function set from the client VTable record (block 111). Next, the class VTable record (a set record) is retrieved based on the class ID (block 112). This step can be accomplished using the class link pointer for cached classes or function sets, or requires a lookup in the class catalog. Once the class VTable record is found, a link engine, generally outlined by dotted line 94, executes. The first step in the link engine is to get the function array pointer from the class VTable record (block 113). Next, the array is searched for the particular called function (block 114). Next, a pointer to the function is stored in the stub record for the client providing a function link cache value (block 115). Finally, the function pointer is returned to the second level dispatch routine (block 116). The second level dispatch routine then cleans up the process and jumps to the function (block 117).

FIGS. 6A, 6B, and 6C provide a flowchart for the step of block 112 in FIG. 5B, which returns a class VTable record in response to the class ID. Thus, the algorithm begins by taking the class ID as input (block 150).

Using the class ID, the class catalog object is called which first compares the class serial number in the client VTable record to a global start serial number maintained by the shared library manager. The shared library manager insures that all serial numbers of valid clients are at least greater than the global start serial number.

If this test succeeds, then the algorithm loops to block 152 where it is determined whether the class link pointer in the client VTable is null. If it is null, then the algorithm branches to block 161 in FIG. 6B. However, if the pointer is not null, then the class record is retrieved based on the information in the link pointer.

After retrieving the TClass record, the class serial number in the client VTable is compared with the same in the TClass record. If they do not match, then the algorithm branches to block 161. If they do match, then the library record TLibrary for the class is retrieved from the information in TClass (block 155). The library record indicates whether the VTables for the class are initialized (block 156). If they are not, then the algorithm branches to block 162. If they are initialized, then the "code" serial number in the client VTable is compared with the same in the library record (block 157). If they do not match, then the algorithm branches to block 162.

If the code serial numbers match, then the class VTable record is returned in response to the information in the TClass record (block 158).

After retrieving the class VTable record, the class VTable record use count is incremented as well as the library use count (block 159). After block 159, the algorithm is done, as indicated in block 160.

FIG. 6B illustrates the routine for handling the branches from blocks 152, 154, 156, and 157. For branches from blocks 152 and 154, this routine begins with block 161 which calls a lookup class function to get the TClass record from the class catalog (block 161). After retrieving the TClass record, the class VTable record is retrieved in response to the information in TClass (block 162). Next, the class VTable record use count and library use count are incremented (block 163). The class VTable record is reviewed to determine whether it includes pointers to the VTable and the export table for the class (block 164). If there are pointers, then the algorithm is done (block 165). If not, then a set up function is called to initialize the class VTable record (block 166). The setup function is described in FIG. 6C. This algorithm begins with an access to the library record to determine whether the code is loaded (block 167). If the code is loaded, then the library use count is incremented (block 168). If the code is not loaded, then the library is loaded, and its use count incremented (block 169).

After either block 168 or 169, the client VTable record is retrieved from the library, and the pointer to the class VTable record is retrieved (block 170). The pointer taken from the client VTable record in the library is used to get the class VTable record (block 171). Next, the cache links in the client VTable record in the client, and the same in the loaded library, and the cache links in the TClass record are updated with information about the class VTable record (block 172). Finally, the algorithm is done (block 173).

FIG. 7 is a schematic diagram of the structure for the library's files which can be dynamically registered in the class catalog. The library files are normally stored on disk 200. These library files are registered in an extensions folder 201 which is graphically illustrated on the user interface of the device, such as the Macintosh.TM. computer. The extension folder includes a number of management files 202, and a plurality of library files 203, 204, 205. The library files are all registered in the class catalog. The library files having a file type "libr" 206 include a number of segments, including code resources 207, a dictionary "libr" resource 208, and dictionary "libi" resource 209. The code resources 207 include the library code segments such as classes and generic function sets. The dictionary "libr" resource describes the library. Dictionary "libi" resource fists libraries which this library depends on. The dictionary "libr" resource 208 is shown in more detail at block 210. This resource includes a library ID field 211 which is the character string identifying the library. A second field 212 in the structure 210 identifies the code resource type. A third field 213 identifies the template version number for the library file. A fourth field 214 identifies the version number of the library, which is maintained according to a standard protocol by the developers of the libraries. The next field 215 stores a plurality of library flags. The next field 216 identifies the number of elements in an exported class information array 217. This information array 217 includes one record per exported class in the library. Each record includes a class identifier 218, class flags 219, a version number of the current version of the class 220, a minimum version number for the backward compatible version number for the class 221, a number 222 which indicates the number of elements in the following array 223 of parent class IDs. The army 223 of parent class IDs includes the identifier of each parent of the class. The information in this resource 210 is used to create the class information records for the class catalog upon registration of the library.

FIG. 8 illustrates the basic algorithm for dynamically registering libraries using the structure of FIG. 7.

As indicated at block 300, the operating system designates a special folder such as Extensions folder 201 in FIG. 7, and applications may designate additional folders for registered libraries.

The Library Manager intercepts operating system calls which indicate a file has been copied or moved. Then it is determined whether the file subject of the call is in the special folders or one of the additional folders (block 301).

If a new file is found, then it is determined whether the new file is a shared library resource. If it is, then library is registered in the class catalog by providing information to fill the TClass records for the classes in the class catalog (block 302). If a library has been moved out of the folder, then the library manager will leave it registered until it is no longer in use. After it is no longer in use, then it is moved out of the class catalog (block 303).

The shared library manager also provides functions which are linked to the clients, and allow them to take advantage of the class catalog for various functions. Particular routines include a new object routine which is described with reference to FIGS. 9A and 9B, a variant of the new object routine shown in FIG. 10, a verify object routine shown in FIG. 11, a cast object routine shown in FIG. 12, and a GetClassInfo routine shown in FIG. 13.

As indicated in FIGS. 9A-9B, the new object routine takes as input the class identifier for the new object and an indication of a memory pool for allocation of the object (block 320). Using this information, it is determined whether the memory pool has actually been allocated for the object. If not, then the pool is allocated (block 321). Next, a lookup class function is called in the class catalog to get the TClass object for the identified class (block 322). Next, flags maintained in the TClass object indicate whether the new object routine is supported for the particular class (block 323). If it is supported, then it is determined whether the TClass record for the class is associated with a library other than the root library. If it is a root library class, then it is guaranteed to be always loaded, and the use content is incremented (block 324).

If the class is associated with a library other than a root library, a load function is called to either load the library and then increment the use count, or if the library is already loaded then just increment the use count (block 325).

Next, the TClass object is used to retrieve the class VTable record (block 326). Using the flags in the class VTable record, it is determined whether the new object routine is supported for the class (once again) (block 327).

Next, the size of the object is determined from the class VTable record, and memory of that size is allocated to the pool (block 328). Next, a pointer to the allocated memory is retrieved (block 329). The library manager requires that the second slot in the export table for classes in the library contain a pointer to a constructor for the class. Thus, the pointer for the constructor is retrieved from the export table location indicated in the class VTable record (block 330). Using the constructor pointer, the constructor is called which places an object in the allocated memory (block 331).

Next, the use count is decremented by one to balance the use count (block 332). This is required because the load function step of block 325 increments the use count, as does the calling of a constructor in block 330. Thus, the decrementing of the use count is required for balancing the use counts. After the decrementing of use count in block 332, then the algorithm is done (block 333). Thus, a client is able to obtain and call a constructor for a class of which it was not aware at compile time.

FIG. 10 illustrates a variant of the new object routine which has better type safety. In particular, if the client is aware of the parent of the new object to be created, then the variant of FIG. 10 can be called. The variant of FIG. 10 takes as input the parent identifier for the parent of the class, the class ID of the new object to be created, and the memory pool allocation parameters (block 340). Next, a verify class function which is described with respect to FIG. 11 is called to insure that the identified class is derived from the identified parent (block 341). If this verification is successful, then the new object routine of FIGS. 9A and 9B is called for the identified class (block 342). (See Appendix, TLibraryManager::NewObject (two variants)).

FIG. 11 illustrates the verify class routine called in block 341 of FIG. 10. Also, this routine is available to the clients directly. The verify class routine begins by taking the class ID of the base class and of a derived class (block 350). Next, the lookup class function of the class catalog is called to get the TClass record for the derived class (block 351). The TClass record for the derived class will include a list of parent classes. This list is reviewed to determine whether the identified parent class is included (block 352). If the parent class is found, then the algorithm is done (block 353). If the parent class is not found, then go to the TClass record of each parent of the derived class in order. The list of parents for each parent is reviewed to find the identified parent class, following this recursion to the root class. The algorithm ends when the parent is found, or the root class is reached. (See Appendix TLibraryManager::VerifyClass and :: internal VerifyClass).

If there is more than one immediate parent in the list of parents for the TClass record, then a case of multiple inherency is found. In this case, the parent class hierarchy must be reviewed to insure that at least one parent appears as a virtual base class (block 355). If the identified parent in the call of verify class is not found as a virtual base class, then it is determined not related to the derived class for the purposes of this function.

FIG. 12 is a flowchart for a cast object routine executed by the shared library manager and linked to the clients by the required structure of the objects of the shared library manager environment. Using this function, a client can cast an object of a derived class as a parent class object, even though it may not have been aware of the structure of the parent at the time it was compiled. This algorithm takes as input a pointer to the object and an identifier of the parent class (block 400). Next, the class of the object is determined based on the required structure of the object (block 401). This structure involves placing the pointer to the VTable as the first dam member in the object. Also, the first slot in the VTable is a pointer to the VTable record of the shared library manager.

Using the class ID of the object determined from the class VTable record, and the parent ID provided when cast object was called, the verify class routine is then called (block 402). If the verify class succeeds, then it is determined from the class VTable record of the object, whether single or multiple inheritance is the case is found (block 403).

If a case of single inheritance, then the algorithm is done because the offsets are determinate in that case (block 404). If a case of multiple inheritance is encountered, then the correct offsets are found within the object to the data of the parent class (block 405). This can be determined based on the place of the parent class in the hierarchy of parent classes found in the TClass records. (See Appendix TLibraryManager::CastObject and ::interact CastObject).

GetClassInfo is a member function of TLibraryManager, or a non-member function is provided which calls gLibraryManager->GetClassInfo for you. Given a class id which specifies a given base class and an error code pointer it returns a TClassInfo for the given class if the class is registered in the class catalog. The TClassInfo can then be used to iterate over all of the derived classes of the given base class. If the class is not registered or an error occurs GetClassInfo returns NULL. (See Appendix, TLibraryManager::The GetClassInfo).

The GetClassInfo algorithm is shown in FIG. 13. It involves the following: Steps:

1. Call the LookupClass function with the class id. If this returns a pointer that is not NULL then we know that the class is registered with the class catalog. If it returns NULL then set the error code to kNotFound and return NULL for the function return value (block 500).

2. Using the fClasses field of fClassCatalog, which is a TCollection class instance, call the CreateIterator function. If the iterator cannot be created then return NULL for the function return value and set the error code to kOutOfMemory (block 501).

3. Create a TClassInfo instance and set the fIterator field to the iterator returned in step 2. Set the fBaseClassID field to the given class id. If the TClassInfo cannot be created then return NULL as the function return value and set the error code to kOutOfMemory (block 502).

4. Call the Reset function of the iterator to re-start the iteration. Return the TClassInfo as the function return value and set the error code to kNoError (block 503).

The functions of TClassInfo which include using the TClassInfo instance returned by GetClassInfo::

    ______________________________________
    virtual void
                Reset( );
    virtual void*
                Next( ); // safe to cast to TClassID*
                or char*
    virtual Boolean
                IterationComplete( ) const;
    // TClassInfo methods
    TClassID*     GetClassID( );
    Boolean       GetClassNewObjectFlag( ) const;
    Boolean       GetClassPreloadFlag( ) const;
    size.sub.-- t GetClassSize( ) const;
    TLibrary*   GetLibrary( ) const;
    TLibraryFile*
                GetLibraryFile( ) const;
    unsigned short
                GetVersion( ) const;
    unsigned short
                GetMinVersion( ) const;
    ______________________________________
     Copyright Apple Computer 1991-1993


Data members of TClassInfo include:

    ______________________________________
    TClassID           fBaseClassID;
    TClassID           fClassID;
    TLibrary*          fLibrary;
    TLibraryFile*      fLibraryFile;
    unsigned short     fVersion;
    unsigned short     fMinVersion;
    Boolean            fNewObjectFlag;
    Boolean            fPreloadFlag;
    Boolean            fFunctionSetFlag;
    Boolean            fFiller;
    size.sub.-- t      fSize;
    TIterator*         fIterator;
    TClass*            fClass;
    ______________________________________
     Copyright Apple Computer 1991-1993


Reset--starts the iteration over from the beginning.

Next--gets the next derived class in the list.

IterationComplete--returns true if Next has been called for all derived classes of the given base class.

GetClassID--returns the class id of a derived class (fClassID).

GetClassNewObjectFlag--returns true if the class id returned by GetClassID can be used to create an object using the NewObject function.

GetClassPreloadFlag--returns true if the class is preload flag is set to preload the class implementation at boot time.

GetClassSize--returns the size of the data structure for an instance of the class.

GetLibrary--returns the TLibrary for the class.

GetLibraryFile--returns the TLibraryFile for the class.

GetVersion--returns the current version of the class.

GetMinVersion--returns the minimum compatible version of the class.

The algorithm for TClassInfo includes the following steps.

1. When the TClassInfo is created the fBaseClassID field is set to the class id passed to GetClassInfo, the fIterator field is set to a class catalog iterator which iterates the TClass records registered in the class catalog, and fClass is set to the TClass for the class corresponding to fBaseClassID.

2. The function Next sets the data members fClassID, fLibrary, fLibraryFile, fVersion, fMinVersion, fNewObjectFlag, fFunctionSetFlag and fSize. It gets this information from the next TClass record, using the fIterator, which has the desired "is derived from" relationship of the class given by fBaseClassID.

3. The "getter" functions listed above return the information in the corresponding data member of TIterator.

4. The first time the getter functions are called, or after Reset is called, the information returned is for the fBaseClassID class itself.

Source code for the cast object, verify class, new object and get class info routines is provided in the Appendix. Also, the Appendix provides selected class interfaces and functions which may be helpful in understanding a particular implementation of the present invention, when considered with the detailed description of the run-time architecture which follows.

A more detailed description of a particular implementation of the shared library manager is provided below with reference to a code written for the Macintosh.TM. computer.

Overview

The Shared Library Manager (SLM) described herein provides dynamic linking and loading facilities for the 68K Macintosh. The system can be adapted to any platform desired by the user. SLM provides dynamic loading, a.k.a. on-demand loading, both for procedural programs and for C++ programs. This is different from the traditional approach of launch-time loading, also referred to as "full transitive closure", which means that all required libraries are loaded and relocated at once when an application is launched.

SLM provides procedural programming support for exporting and importing functions from C, Pascal, Assembler, or any language with compatible calling conventions. In addition, SLM provides extensive support for exporting and importing C++ classes, with an emphasis on providing the dynamic features which are fundamental to building extensible applications and system components for Macintosh.

Shared libraries can be installed at any time and called in a transparent fashion. There is no dependency when building a client on where the libraries that it uses are, what the filename(s) are, or how many of them may eventually be used during a session. The libraries are loaded and unloaded dynamically based on use counts. The SLM takes care of all of the details of binding and loading, and the client only has to know the interfaces to the classes and functions that it wants to use.

SLM provides facilities for instantiating objects by class name, for enumerating a class hierarchy, and for verifying the class of an object or the class of a class.

Basis of the Architecture

The architecture for SLM is based on the 68K run-time architecture and the MPW tools architecture. A build tool, for the SLM takes an exports file (.exp) and an MPW object file (.o) as input and generates a library file. It does this by processing these files and then calling the MPW linker to finish the job.

For C++ libraries, SLM is based on the MPW/AT&T 2.1 CFront v-table dispatching model. Development tools must generate v-tables compatible with this model. In particular, we assume that the first entry in the v-table is not used--SLM uses it to point to class "meta-data".

SLM also requires the v-table pointer to be the first data member in an object in order for certain functions to work. Since these functions do not know the class of the object (their job is to find out the class) they can only find the class meta-data via the v-table pointer if it is in a known place in the object.

It is theoretically possible for SLM to support more than one dispatching model, however for interoperability it would not be desirable to have more than one model. A dispatching agent could arbitrate between different dispatching models or even different calling conventions which would introduce considerable run-time overhead. It would be possible for different dispatching models to co-exist and yet not interoperate.

SLM and 68K libraries support both single (SI, SingleObject rooted) and multiple inheritance (non-SingleObject rooted) classes.

A development tool wishing to support the SLM in a non-MPW environment will need to generate a `libr` resource, a set of code resources, and optionally, a `libi` resource, a shown in FIG. 7. The jump table resource is not modified at build time--it is a normal model far jump table. It is modified by SLM at load time but the build tools don't need to be aware of this. The glue that does 32-bit relocation and the data initialization glue are code libraries statically linked into the library initialization segment.

Shared libraries have a jump table resource (`code` 0) plus an initialization code segment (`code` 1) plus at least one implementation segment (`code` 2 and up). If more than one library is in a library file then the resource type for each set of code resources must be unique (usually `cd01`, `cd02` etc.).

Library resource--Specifies the type of the `code` resources, and the classes and function sets exported by this library. Of course, the resource ID for each `libr` resource in a file must be unique.

Jump Table resource--Always present in the file, present in memory only if -SegUnload option is used to SLMBuilder. Note that NoSegUnload is the default.

Initialization code segment resource--Only contains code linked to %A5Init or A5Init segment and used at initialization time, must not contain any other code unless -SegUnload option is used to SLMBuilder.

Implementation code segment(s)--Contains any implementation code for the library, including the CleanupProc if any. Often libraries will have only one implementation segment although there is no harm in having more. Implementation segments are numbered 2 and up.

When the SLM loads a library, the jump table resource is loaded, plus the initialization segment. After initialization this segment is released--it will not be needed again unless the library is unloaded and then reloaded.

If the "NoSegUnload" option is used (NoSegUnload option to LibraryBuilder is the default) then all code segments are loaded. The jump table plus the relocation information generated for each segment is used to relocate the jump table based addresses in the code to absolute addresses pointing to the target function in the target code resource. The jump table resource is then released. When using this option the library should normally have only one implementation segment but this is not a requirement.

If the "SegUnload" option is used (SegUnload option to LibraryBuilder) then the implementation segment is loaded, plus any segments designated preload (preload resource bit can be set on a per-segment basis from a statement in the .r file), or all segments are loaded if a library itself is designated preload (preload flag in the Library descriptor). Each jump table based reference in the code is relocated to point to the absolute address of the jump table entry. The jump table is modified to contain pc-relative jsr instructions instead of segment loader traps. The jsr goes to the SLM segment loader entry point just before the jump table (in the 32 byte gap). This limits the size of the jump table to 32K, which should not be a problem since libraries should not be huge bodies of code--library files can easily have multiple libraries in them if packaging is an issue. It is a jsr and not a jmp since the segment loader uses the return address, which now points to the last two bytes of the jump table entry, to compute which segment is to be loaded. At load time the SLM moves the segment number information out of the jump table entry to an array following the jump table. This is due to the fact that the jsr pc relative takes 2 more bytes than the original segment loader trap. Note that all the machinations on the jump table are transparent to a tool developer.

A segment is loaded when a jump table (jt) entry is called and the jump table is then modified to contain an absolute jump for all jt entries for that segment. When segments are unloaded, the pc relative jsr is put back in the jump table for each entry for that segment.

The data segment based addresses (the "global world", i.e. what would have been A5 based) are relocated to the absolute address of the data.

Building a Shared Library

Any application, extension, driver, or other stand-alone code resource on the Macintosh can use shared libraries. Of course, a client can also be another shared library. A shared library can import and export functions or classes. A non-library client (for brevity, an "application") can only import functions or classes. An application can sub-class an imported class, but it cannot export a class. This is a minor limitation since an application can contain shared libraries as resources in the application itself, or register a special folder containing shared libraries that are effectively part of the application.

The Shared Library Manager accomplishes it's sharing by examining and modifying the object file destined to become a shared library. It generates several source and resource files that are then used to create the shared library and to provide clients with linkable "stubs" to gain access to the functions and classes in the shared library. In the sections which follow, we will examine each of these files.

Dispatching Architecture

First and foremost of the files generated by the SLM LibraryBuilder tool is the file SharedLibTemp.stubs.a. This is an assembly language file that contains the stubs for all of the functions that are exported. Exported functions fall into five categories. They are: 1) function set function; 2) class constructor; 3) class destructor; 4) class virtual functions; and 5) class non-virtual functions. There is a separate dispatching function for each of these classifications, and the stubs are generated slightly different for each. Each one will be examined in detail shortly. For the purposes of explaining the architecture, an exported function in a function set will be used.

For each dispatching function, there are 5 parts. The first two parts are supplied by the build tool, and are unique for each function. The other 3 parts are supplied by the SLM.

The first part is a structure called a stub record (see FIG. 6).

    ______________________________________
    .sub.-- stbSample RECORD
                      EXPORT
    IMPORT            .sub.-- CVRExampleFSet:Data
    DC.L              0
    DC.L              .sub.-- CVRExampleFSet
    DC.L              0
    DC.W              3
    ENDR
    ______________________________________
     Copyright Apple Computer 1991-1993


The stub record contains 2 fields used internally by the Shared Library Manager (the first and third fields in the example shown above). The second field is a pointer to the ClientVTableRec. The ClientVTableRec is a structure (see FIG. 6) that is linked with the application that has all of the information that the SLM needs to dynamically find and load the function set or class referenced by the stub.

This is the "C" definition of the ClientVTableRec:

    ______________________________________
    TLink*           fClassLinkPtr;
    long             fClassSerialNumber;
    long             fCodeSerialNumber;
    short            fVersion;
    short            fMinVersion;
    char             fClassIDStr[2];
    };
    ______________________________________
     Copyright Apple Computer 1991-1993


The fClassLinkPtr field contains information used by the SLM to cache the link to the internal TClass object which contains all of the information known about the class or function set. The two serial number fields are used to insure that the cached information is still valid (if the library unloaded and a new version of a class or function set in the library was dragged into a registered folder, any cached information is invalid). The version number fields contain information about the version number of the class or function set that your application (code resource, extension, etc.) linked with, and the fClassIDStr field contains the actual ClassID of the class or function set so that it can be found in the SLM catalog.

The last field in the stub record is an index. It tells the SLM which entry in the function set VTable contains a pointer to the desired function.

Most stub dispatching comes in 3 speeds--very fast, fast, and slow. Very fast dispatching occurs when you have already used the function before. In this case, the first field of the stub record contains the address of the actual function, and can be called immediately. If you have never called this function before, then a dispatching stub is called which causes the SLM to examine the ClientVTableRec. If you have already used another function in this same class or function set, then the ClientVTableRec already contains cached information as to the location of the tables containing the function addresses. In this case, your stub is updated so that the address of the function is cached for next time, and the function is then called. If the ClientVTableRec does not contain cached information, then the SLM must look up the class or function set by the ClassID stored in the ClientVTableRec, load the library containing the class or function set if it is not already loaded, update the cached information in the ClientVTableRec, update the cached information in the stub, and then finally call the function.

The second part of the dispatching mechanism is the actual stub code that a client links with:

    __________________________________________________________________________
    Sample
        PROC EXPORT
    IMPORT    .sub.-- stbSample:Data
    IF MODEL = 0 THEN
    lea       .sub.-- stbSample,a0
                       ;Get the stub record into a0
    ELSE
    lea       (.sub.-- stbSample).L,a0
    ENDIF
    move.I    (a0),d0  ; Get the cached function address
    beq.s     @1       ; Not cached - do it the hard way
    move.I    d0,a0    ; Get address into a0
    jmp       (a0)     ; and jump to it
    IMPORT    .sub.-- SLM 1 1 FuncDispatch
    @1
    IF MODEL = 0 THEN
    jmp       .sub.-- SLM 1 1 FuncDispatch
                          ; More extensive dispatching needed
    ELSE
    jmp       (.sub.-- SLM 1 1 FuncDispatch).L
    END
    IF MACSBUG = 1 THEN
    rts
    DC.B      $80, $06
    DC.B      Sample
    DC.W      0
    ENDIF
    ENDP
    __________________________________________________________________________
     Copyright Apple Computer 1991-1993


Normally two (or maybe four) versions of the stub are assembled--one in model near (MODEL=0), and one in model far (MODEL=1). There may also be debugging versions generated with Macsbug symbols for each (MACSBUG=1).

Notice that the first thing that the stub does is to check whether the first field of the stub record is non-zero. If it is, it just jumps through the pointer stored there. Otherwise, it calls a first level dispatching function called .sub.-- SLM11FuncDispatch (or one of the other 4 variations of this function).

This function is the third part of the dispatching code:

    ______________________________________
    .sub.-- SLM 1 1 FuncDispatch
                    PROC  Export
    move.I      $2B6,a1
    move.I      $10C(a1),a1
    move.I      SLMGlobal.fStubHelp + 16(a1),a1
    IF      MODEL = 0 THEN
    move.I      .sub.-- gLibraryManager,d0
    ELSE
    move.I      (.sub.-- gLibraryManager).L,d0
    ENDIF
    jmp          (a1)
    ENDP
    ______________________________________
     Copyright Apple Computer 1991-1993


The first two instructions fetch the SLM globals. The SLM stores it's global information in a low-memory structure known as the ExpandMemRec (location $2B6 in the Macintosh contains a pointer to this structure). The SLM global information is stores as a pointer at offset $10C in this structure. One of the fields in this structure contains a vector of dispatch functions. This dispatcher uses the 5th element in the vector to dispatch through (this is the vector to dispatch functions in function sets).

The code for this dispatching function (and the other four variations) are supplied in LibraryManager.o and LibraryManager.n.o, so clients can link with it.

The fourth part of stub dispatch is the second level dispatching function that is stored in this vector:

    ______________________________________
    SLMFuncDispatch
                PROC    Export
    move.1  d0,-(sp) ; Push the library manager
    move.1  a0,-(sp) ; Push the stub record
    move.1  d0,a0    ; Put TLibraryManager into a0
    move.1  20(a0),a0
                     ; Get the class catalog
    move.1  a0,-(sp)
    move.1  (a0),a0
    move.1  CatVTable.LookupFunction(a0),a0
    jsr     (a0)     ; Call the LookupFunction method
    lea     12(sp),sp
                     ; Drop parameters
    move.1  d0,a0    ; Get the function
    jmp     (a0)     ; Call it
    ______________________________________
     Copyright Apple Computer 1991-1993


This dispatcher calls a function in the TClassCatalog object, which is the fifth and final part of stub dispatch. A partial declaration for TClassCatalog follows.

    __________________________________________________________________________
    #define kTClassCatalogID
                  "!$ccat, 1.1"
    typedef ClientVTableRec
                 CVR;
    typedef FunctionStubRec
                 FSR;
    typedef void (*VF)(void);
    typedef VTable
                 VF[ ];
    class TClassCatalog : public TDynamic
                  TClassCatalog( );
    virtual      .about.TClassCatalog( );
    //
    // These first functions are here for backward compatibility with
    // SLM 1.0
    //
    #if COMPAT10
    virtual VR   ExecDestructor(CVR*) const;
    virtual VR   ExecConstructor(CVR*, size.sub.-- t idx) const;
    virtual VR   ExecVTableEntry(CVR*, size.sub.-- t idx) const;
    virtual VR   ExecExportEntry(CVR*, size.sub.-- t idx) const;
    virtual void ExecFunction(FSR*, TLibrary Manager*) const;
    virtual VR   ExecRootDestructor(CVR*) const;
    virtual VR   ExecRootConstructor(CVR*, size.sub.-- t idx) const;
    virtual VR   ExecRootVTableEntry(CVR*, size.sub.-- t idx) const;
    virtual VR   ExecRootExportEntry(CVR*, size.sub.-- t idx) const;
    #endif
    virtual VF   LookupFunction(FSR*, TLibraryManager*);
    virtual VTableRec*
                 GetVTableRecMemory(size.sub.-- t num) const;
    virtual VTableRec*
                 Init1VTableRec(VTableRec*, ProcPtr setupProc,
                  CVR* client) const;
    virtual VTableRec*
                 InitVTableRec(VTableRec*, VTable vTable,
                    VTable exportTable, CVR* parent,
                    long size, char*) const;
    virtual VTableRec*
                 InitVTableRec(VTableRec*, VTable exportTable,
                    char*) const;
    #if COMPAT10
    virtual VTableRec*
                 GetGenVTableRec(CVR*) const;
    #endif
    virtual VTableRec*
                 LookupVTableRec(CVR* theClient) const;
    virtual VTableRec*
                 GetVTableRec(CVR*, Boolean isSub) const;
    virtual VTableRec*
                 ReleaseVTableRec(CVR*) const;
    virtual OSErr
                  InitLibraryManager(TLibraryManager**, long*,
                    size.sub.-- t poolsize,
                  ZoneType theZone,
                  MemoryType theMemType);
    virtual Boolean
                 CleanupLibraryManager(TLibraryManager**);
    virtual VF   GetDestructor(FSR*, TLibraryManager*) const;
    virtual VF   GetConstructor(FSR*, TLibraryManager*,
                      Boolean isSub) const;
    virtual VF   GetVTableEntry(FSR*, TLibraryManager*) const;
    virtual VF   GetExportEntry(FSR*, TLibraryManager*) const;
    virtual VTableRec*
                 GetParentVTableRec(CVR*) const;
    };
    __________________________________________________________________________
     Copyright Apple Computer 1991-1993


There are five routines in the TClassCatalog, corresponding to each of the five dispatch methods. They are: 1) LookupFunction; 2) GetConstructor; 3) GetDestructor; 4) GetVTableEntry; and 5) GetExportEntry.

It is not necessary that any generated code know vtable offsets into the class catalog. These offsets are known by the vectorized dispatch code. In fact, the dispatch code was vectorized specifically so that offsets in the TClassCatalog could change without causing recompilation of clients.

This fifth and final dispatch routine does the actual finding of the class, and storing of any cached values.

In the code examples that follow, code and structures that have a bold header and trailer is code that must be generated by a build tool in order to create a shared library. Code that is not in bold is shown only for reference.

Generating Function Set Code

To import a function a client has to include the interface file when compiling (in C, the .h file), and link with client object file (.cl.o or .cl.n.o) provided by the library developer. The client object file contains the client stubs for the functions that the client calls.

Consider the following example function set which is exported by the ExampleLibrary.

This is the FunctionSet declaration in the exports file (ExampleLibrary.exp):

    __________________________________________________________________________
    FunctionSet ExampleFSet
      id = kExampleFunctionSet;
    //
    //We could use the following export line, but we want all exported
    //functions from the library to be exported, so we say nothing!
    //
    // exports = Hello, extern HelloC, pascal extern HelloPascal, Goodbye,
    //    pascal GoodbyePascal, TExampleClass::Test;
    };
    __________________________________________________________________________
     Copyright Apple Computer 1991-1993


These are the prototypes from the interface file (ExampleLibrary.h):

    ______________________________________
    char* Hello(ulong&);
    char* Hello(ulong*);
    extern "C" char* HelloC(ulong*);
    ulong Goodbye( );
    pascal Ptr HelloPascal(ulong& theHelloTicks);
    pascal ulong GoodbyePascal( );
    ______________________________________
     Copyright Apple Computer 1991-1993


Function Set Function Dispatching (Stubs)

The build tool, LibraryBuilder, generates stubs to be linked with the client for each FunctionSet function exported by a given library.

A stub is generated for each function. Here is the stub record and the stub that is generated for the "HelloC" function (in SharedLibTemp.stubs.a):

    ______________________________________
    .sub.-- stbHelloC
              RECORD    EXPORT
    IMPORT         .sub.-- CVRExampleFSet:Data
    DC.L           0
    DC.L           .sub.-- CVRExampleFSet
    DC.L           0
    DC.W           3
    ENDR
    HelloC    PROC      EXPORT
    IMPORT         .sub.-- stbHelloC:Data
    IF MODEL = 0 THEN
    lea            .sub.-- stbHelloC,a0
    ELSE
    lea            (.sub.-- stbHelloC).L,a0
    ENDIF
    move.I         (a0),d0
    beq.s          @1
    move.I         d0,a0
    jmp            (a0)
    IMPORT         .sub.-- SLM 1 1 FuncDispatch
    @1
    IF MODEL = 0 THEN
    jmp            .sub.-- SLM 1 1 FuncDispatch
    ELSE
    jmp            (.sub.-- SLM 1 1 FuncDispatch).L
    END
    IF MACSBUG = 1 THEN
    rts
    DC.B           $80, $0B
    DC.B           `stub.sub.-- HelloC`
    DC.W           0
    ENDIF
    ENDP
    ______________________________________
     Copyright Apple Computer 1991-1993


This is the structure of the stub record in C:

    ______________________________________
    struct FunctionStubRec
    VirtualFunction      fFunction;
    ClientVTableRec*     fClientVTableRec;
    FunctionStubRec*     fNextStubRec;
    unsigned short       fFunctionID;
    };
    ______________________________________
     Copyright Apple Computer 1991-1993


When the stub is called, it first checks to see if the address of the function is already cached. If so, it jumps immediately to the function. Otherwise, it jumps to the function dispatcher (.sub.-- SLM11FuncDispatch) with the stub record as a parameter in register A0. The stub dispatcher then obtains the address of the actual dispatching code from a low-memory global set up when SLM was originally loaded, and it jumps to that code. This extra indirection allows SLM the flexibility to modify the function loading and dispatching mechanism without affecting client code (since clients are linked with the .sub.-- SLM11FuncDispatch code).

This is the function dispatcher that is linked with the client.

    ______________________________________
    .sub.-- SLM 1 1 FuncDispatch
                    PROC    Export
    move.I       $2B6,a1
    move.I       $10C(a1),a1
    move.I       SLMGlobal.fStubHelp + 16(a1),a1
    IF      MODEL = 0 THEN
    move.I       .sub.-- gLibraryManager,d0
    ELSE
    move.I       .sub.-- gLibraryManager).L,d0
    ENDIF
    jmp           (a1)
    ENDP
    ______________________________________
     Copyright Apple Computer 1991-1993


This is the actual function dispatcher that is linked with the Shared Library Manager for reference:

    ______________________________________
    .sub.-- SLMFuncDispatch
                PROC  Export
    move.I  d0,-(sp)  ; Push the library manager
    move.I  a0,-(sp)  ; Push the stub record
    move.I  d0,a0     ; Put TLibraryManager into a0
    GetClassCatalog a0
                  ; Get the class catalog into a0
    move.I  a0,-(sp)  ; Push it
    move.I  (a0),a0   ; Get the VTable
    move.I  CatVTable.LookupFunction(a0),a0
                             ; Get the
                               function
    jsr     (a0)      ; Call it
    lea      12(sp),sp
                      ; Pop the parameters
    move.I   d0,a0    ; Get the function address
    jmp      (a0)     ; jump to it
    ENDP
    ______________________________________
     Copyright Apple Computer 1991-1993


The CatVTable.LookupFunction is a call to the TClassCatalog::LookupFunction method.

A ClientVTableRec is generated per function set (to be linked with the client in SharedLibTemp.stubs.a):

    ______________________________________
    .sub.-- CVRExampleFSet
                      RECORD    EXPORT
            DC.L  0, 0, 0
            DC.W  $0100
            DC.W  $0000
            DC.B  `appl:exam$ExampleFSet`, 0
            ENDR
    ______________________________________
     Copyright Apple Computer 1991-1993


Function Set Function Dispatching (Initialization)

The initialization code is generated in two files: SharedLibTemp.init.a and SharedLibTemp.init.c. Most of the generated code is in "C", but for each class or function set, a ClientVTableRec is generated which is put into the assembly file. It is possible to put the ClientVTableRec definition in "C" (the inline "C"-string makes it a little more challenging, but it can be done), but we chose to leave it in assembly. Strictly speaking, if your initialization code is going to link with your stub library, a ClientVTableRec does not need to be generated for initialization, but it makes things easier just to generate one as a matter of course.

The vector table is generated into SharedLibTemp.Init.c (to be linked with the library):

    ______________________________________
    typedef void (*ProcPtr)(void);
    ProcPtr.sub.-- vtbI.sub.-- ExampleFSet[ ] =
    0,                // First entry is normally 0
    (ProcPtr)Hello.sub.-- FRUI,
    (ProcPtr)Hello.sub.-- FPUI,
    (ProcPtr)HelloC,
    (ProcPtr)HELLOPASCAL,
    (ProcPtr)Goodbye.sub.-- Fv,
    (ProcPtr)GOODBYEPASCAL,
    (ProcPtr)Test.sub.-- 13TExampleClassSFUI,
    (ProcPtr)Test.sub.-- 13TExampleClassSFPc,
    0,
    };
    ______________________________________
     Copyright Apple Computer 1991-1993


The SLM allows functions to be exported by name, as well. If any functions are exported by name, one more structure is created. Assuming that the HelloC routine and the GOODBYEPASCAL routine were to be exported by name, the following extra code would be generated:

    ______________________________________
    static char .sub.-- Str.sub.-- Sample.sub.-- 2[ ] = "HelloC";
    static char .sub.-- Str.sub.-- Sample.sub.-- 2[ ] = "GOODBYPASCAL";
    char* SampleNameStruc[ ] =
    (char*)-1L,
    (char*)-1L,
    .sub.-- Str.sub.-- Sample.sub.-- 1,
    (char*)-1L,
    .sub.-- Str.sub.-- Sample.sub.-- 2,
    };
    ______________________________________
     Copyright Apple Computer 1991-1993


Any slot corresponding to a function that is not exported by name is filled with a (char*)-1L. A slot with a NULL (0) pointer terminates the list of names. A pointer to this list of names is stored in the first entry of the vector table:

    ______________________________________
    ProcPtr.sub.-- vtbl.sub.-- ExampleFSet[ ] =
           (ProcPtr)SampleNameStruc,
           (ProcPtr)Hello.sub.-- FRUI,
           (ProcPtr)Hello.sub.-- FPUI,
           (ProcPtr)HelloC,
           (ProcPtr)HELLOPASCAL,
           (ProcPtr)Goodbye.sub.-- Fv,
           (ProcPtr)GOODBYEPASCAL,
           (ProcPtr)Test.sub.-- 13TExampleClassSFUI,
           (ProcPtr)Test.sub.-- 13TExampleClassSFPc,
           0,
    };
    ______________________________________
     Copyright Apple Computer 1991-1993


An initialization function is generated for each function set.

First, let's show you the header generated for the initialization file (generated in SharedLibTemp.init.c):

    ______________________________________
    typedef struct ClientVTableRec
    long   l1;
    long   l2;
    long   l3;
    short  v1;
    short  v2;
    char   name[ ];
    } ClientVTableRec;
    void Fail(long err, const char* msg);
    extern void** .sub.-- gLibraryManager; //A convenient lie?
    extern void.sub.-- pure.sub.-- virtual.sub.-- called(void);
    typedef void (*ProcPtr)(void);
    typedef struct.sub.-- mptr { short o; short i; ProcPtr func; } .sub.--
    mptr;
    typedef ProcPtr* VTable;
    typedef void
             (*SetupProc)(void*, unsigned int);
    typedef void*
             (*Init1VTableRec)(void*, void*, SetupProc,
             ClientVTableRec*);
    typedef void*
             (*InitVTableRec)(void*, void*, VTable, VTable,
             ClientVTableRec*, unsigned int, char*);
    typedef void*
             (*GetVTableRec)(void*, ClientVTableRec*,
             unsigned char);
    typedef void*
             (*ReleaseVTableRec)(void*, ClientVTableRec*);
    typedef void*
             (*InitExportSet)(void*, void*, VTable, char*);
    typedef void*
             (*GetVTableMemory)(void*, unsigned int);
    #define GetClassCatalog (.sub.-- gLibraryManager[5])
    ______________________________________
     Copyright Apple Computer 1991-1993


Now the SVR (SVR stands for Setup VTableRec) function (generated in SharedLibTemp.init.c):

    ______________________________________
    #pragma segment A5Init
    void.sub.-- SVRExampleFSet(void* vtRec, unsigned int vtRecSize)
    register ProcPtr toCall;
    void** catalog = GetClassCatalog; // Get Class Catalog
    void** ctVTable = *catalog; // Get it's VTable
    //
    // Get pointer to 22nd entry, which is InitExportSet
    // function
    //
    toCall = (ProcPtr)ctVTable[22];
    //
    // Call it with the following parameters:
    // 1)  The pointer to the class catalog
    // 2)  The vtable record pointer passed in to your function
    // 3)  A pointer to the vtable we created for the
           function set.
    // 4)  A zero for future expansion
    //
    (*(InitExportSet)toCall)(catalog,
    vtRec, .sub.-- vtbl.sub.-- ExampleFSet, 0);
    }
    ______________________________________
     Copyright Apple Computer 1991-1993


The first parameter to the SVR function is known as the VTableRec.

This is the definition of the VTableRec structure. This information is for reference only.

    ______________________________________
    struct VTableRec
    VTable          fVTablePtr;
    VTable          fExportTable;
    TUseCount       fUseCount; // "long" in size
    void*           fReserved;
    ClientVTableRec*
                    fParentClientPtr;
    unsigned short  fSize;
    unsigned        fParentIsVirtual:1;
    unsigned        fFiller:1;
    unsigned        fCanNewObject:1;
    unsigned        fIsFunctionSet:1;
    unsigned        fIsRootClass:1;
    unsigned        fLocalCVRIsParent:1;
    unsigned        fIsParentVTable:1;
    unsigned        fIsMasterOrLast:1;
    unsigned char   fDispatcher;
    ClientVTableRec*
                    fLocalClientPtr;
    union
    {
    SetupProc          fSetup;
    TRegisteredObjects*
                         fRegisteredObjects;
    };
    };
    ______________________________________
     Copyright Apple Computer 1991-1993


The VTableRec is used internally by the SLM to keep track of information about each function set or class. Library initialization code supplies all of the information the SLM needs to fill in the VTableRec.

One initialization function per library is generated which calls the SLM to register all of the ClientVTableRecs and SVR functions. This example shows initialization for the example library, which has the function set ExampleFSet and the class TExampleClass. Those parts of this code that you would change depending on what you are initializing are underlined.

    ______________________________________
    #pragma segment A5Init
    void*.sub.-- InitVTableRecords(void)
    register ProcPtr toCall;
    void* vtRec;
    void* savedRec;
    void** catalog = GetClassCatalog;
                      // Get Class Catalog
    void** ctVTable = *catalog;
                      // Get it's VTable
    //
    //    Get the pointer to GetVTableMemory, and call it, asking
    //    for memory for 2 VTableRecs (Of course, you would ask
    //    for the number of VTableRecs that you need).
    //
    toCall = (ProcPtr)ctVTable[19];
    savedRec = (*(GetVTableMemory)toCall)(catalog,2);
    //
    //    Get the pointer to the Init1VTableRec method
    //
    toCall = (ProcPtr)ctVTable[20];
    //
    //    Start `vtRec` pointing to the memory that we got.
    //
    vtRec = savedRec;
    //
    //    Call Init1VTableRec for our first export (a Class,
          in this
    //    case). Parameters are:
    // 1) The class catalog
    // 2) The VTableRec Memory
    // 3) A pointer to the "SetupVTableRec" procedure
    // 4) A pointer to the local "ClientVTableRec"
    //    The method will return a pointer to the next
    //    VTableRec for use with additional initialization.
    //    Using this method, it is not required for you to
          "know" the size of a VTableRec
    //
    vtRec = (*(Init1VTableRec)toCall)(catalog, vtRec,
                  .sub.-- SVRTExampleClass,
                  &.sub.-- CVRTExampleClass);
                  //
    //    Do it for the next export (a function set, in this example)
    //
    vtRec = (*(Init1VTableRec)toCall)(catalog,
                  vtRec,.sub.-- SVRExampleFSet,
                  &.sub.-- CVRExampleFSet);
                  //
    // Return a pointer to the original VTableRec
    //
    return savedRec;
    }
    ______________________________________
     Copyright Apple Computer 1991-1993


Singly-Inherited Classes (Stubs)

This section will examine the stub creation for a C++ class which is singly-inherited. This includes both forms of vtables--SingleObject derived, and standard AT&T v2.1 classes. Classes which are multiply-inherited (derive from more than 1 parent class) are handled in a separate section.

Here is the definition of the TExampleClass (from ExampleClass.h)

    ______________________________________
    #define kTExampleClassID "appl:exam$TExampleClass,1.1"
    class TExampleClass : public TDynamic
    public:
                  TExampleClass( );
    virtual       .about.TExampleClass( );
    // New Methods
    virtual char* GetObjectName( ) const;
    virtual void  SetObjectName(char *theName);
    virtual void  DoThisAndThat( );
    virtual void  DoThat( );
    virtual void  SetGlobalInt(long theValue);
    virtual long  GetGlobalInt( );
    // Public non-virtual function
    // Dynamically exported by using ExportFunction
    void          GetGlobalRef(long*&);
    // Public static function
    // Dynamically exported by the ExportFunction
    static Boolean
                  Test(ulong test);
    static Boolean
                  Test(char* test);
    private:
    char *fName;
    //      static gExampleClassCount counts the
            number of instances
    static long     gExampleClassCount;
    };
    ______________________________________
     Copyright Apple Computer 1991-1993


Constructor Stubs

Constructor stubs are generated for each constructor of a class. If the export file specifies that no constructor stubs are to be exported (using the noMethodStubs or noStubs flag), then the constructor stubs must be created in the assembly language portion (SharedLibTemp.Init.a) of the initialization file. This is so that use counts can be properly maintained for every class.

A stub record is generated to be linked with both the client and the library (in SharedLibTemp.stubs.a or SharedLibTemp.init.a, as appropriate). This record is used much like the record for a function set--It contains cached information that is used to speed up the dispatching. In addition, it contains the index into the "structor table" for the actual address of the constructor (see the class initialization section for information on creating this table).

    ______________________________________
    .sub.-- stb.sub.-- ct.sub.-- 13TExampleClassFv RECORD EXPORT
    IMPORT    .sub.-- CVRTExampleClass:Data
    DC.L      0
    DC.L      .sub.-- CVRTExampleClass
                                ; ClientVTableRec
    DC.L      0
    DC.W      3                 ; Index into table
    ENDR
    ______________________________________
     Copyright Apple Computer 1991-1993


A constructor stub is generated to be linked with both the client and the library (in SharedLibTemp.stubs.a or SharedLibTemp.init.a, as appropriate):

    ______________________________________
    .sub.-- ct.sub.-- 13TExampleClassFv PROC EXPORT
    IMPORT      .sub.-- stb.sub.-- ct.sub.-- 13TExampleClassFv:Data
    IF MODEL = 0
    LEA         .sub.-- stb.sub.-- ct.sub.-- 13TExampleClassFv,a0
    ELSE
    LEA         (.sub.-- stb.sub.-- ct.sub.-- 13TExampleClassFv).L,a0
    ENDIF
    IMPORT      .sub.-- SLM11ConstructorDispatch
    IF MODEL = 0
    JMP         .sub.-- SLM11ConstructorDispatch
    ELSE
    JMP         (.sub.-- SLM11ConstructorDispatch).L
    ENDIF
    IF MACSBUG = 1 THEN
    rts
    DC.B        $80, $1C
    DC.B        `stub.sub.-- ct.sub.-- 13TExampleClassFv`
    DC.B        0
    DC.W        0
    ENDIF
    ENDP
    ______________________________________
     Copyright Apple Computer 1991-1993


Notice that the constructor does not use any cached information to jump to the constructor directly. This is so that use counts may be updated (see the next bullet point).

This is the constructor function dispatcher that is linked with the client. This is for reference only--the client should link with the version supplied by SLM.

    __________________________________________________________________________
    .sub.-- SLM11ConstructorDispatch PROC Export
    WITH   FunctionStubRec
    tst.l  (a0)             ; Constructor pointer cached?
    beq.s  @2               ; No - do it the hard way
    move.l clientCVR(a0),a1 ; Get the ClientVTableRec
    move.l (a1),a1          ; Get the ClassLinkPtr
    move.l 4(a1),a1         ; Get the TClass
    move.l TClass.vtRec(a1),a1
                            ; Get the VTableRec pointer
    addq.l #1,VTRec.useCount(a1)
                            ; Increment the use count
    beq.s  @1               ; Have to do the library count?
    move.l (a0),a0          ; No - go on
    jmp    (a0)             ; Jump to the constructor
    ; Here, we have to bump the libraries use count - so we
    ; call the SLMConstructorDispatch function - but first, we
    ; have to back off the VTableRec use count we just incremented
    ;
    @1 subq.1
           #1,VTRec.useCount(a1)
                            ; Back off the VTableRec use count
    @2
    move.l $2B6,a1
    move.l $10C(a1),a1
    move.l SLMGlobal.fStubHelp + 4(a1),a1
    IF MODEL = 0 THEN
    move.l .sub.-- gLibraryManager,d0
    ELSE
    move.l (.sub.-- gLibraryManager).L,d0
    ENDIF
    jmp    (a1)
    ENDP
    __________________________________________________________________________
     Copyright Apple Computer 1991-1993


Under normal circumstances, the bumping the use count of the VTableRec is all that is required, so dispatching is moderately fast. The only time that the more general dispatching mechanism needs to be invoked is if the constructor has never been invoked by the current client before, and there are no outstanding instances of this class among all clients of the SLM.

Of course, if your compiler has a different naming convention for constructors, you must generate stubs that have the same name as the ones generated (See the initialization section for more information).

This is the actual constructor function dispatcher that is linked with the Shared Library Manager. This is for reference only:

    ______________________________________
    SLMConstructorDispatch PROC Export
    move.l    d0,a1    ; Save the library manager in a1
    moveq     #1,d0
    ; We test the "this" pointer to see if it's NULL. If it is, then
    ; the object is being "newed", so we set d0 to 0, to tell the SLM
    ; that we are fetching a primary object, and not a subclass. This
    ; allows the SLM a little more latitude in version matching.
    ;
         tst.l    4(sp)    ; Check the "this" pointer
         bne.s    @1
         moveq    #0,d0
    @1   move.l   d0,-(sp) ; Push the "isSubClass" flag
         move.l   a1,-(sp) ; Push the library manager
         move.l   a0,-(sp) ; Push the stub record
         move.l   20(a1),a0
                           ; Get class catalog from lib mgr
         move.l   a0,-(sp) ; Push it
         move.l   (a0),a0  ; Get it's vtable
         move.l   CatVTable.GetConstructor(a0),a0
         jsr      (a0)     ; Call the GetConstructor entry
         lea      16(sp),sp
                           ; Drop parameters
         move.l   d0,a0    ; Fetch constructor address
         jmp (a0)          ; Jump to it
         ENDP
    ______________________________________
     Copyright Apple Computer 1991-1993


The CatVTable.GetConstructor is a call to the TClassCatalog::GetConstructor method.

Destructor Stubs

Destructor stubs are generated for the destructor of an