When you define a static object with the DEFINE statement, ABL knows everything it needs to know about the object at compile time. In addition to setting up the object’s description in r-code at compile time, ABL defines a scope for the object. Define Graphical Objects discussed object scope. Any defined object has a name, and a reference to that object has to be within its scope. Outside its scope the object name has no meaning and causes a compile-time error.

By contrast, a dynamic object has no particular scope in terms of procedure blocks. It can be referenced and used by any part of the application that has access to its handle from the time it is created until it is deleted. You can explicitly delete an individual dynamic object or you can place that object into a pool of memory where its storage is allocated and then delete the object by deleting its memory pool. It is especially important to keep in mind that the existence of a dynamic object has nothing to do with the scope of the handle variable you associate it with. For example, look at the following two-line procedure:

DEFINE VARIABLE hButton AS HANDLE NO-UNDO.
CREATE BUTTON hButton.

When the procedure terminates, the hButton variable goes out of scope and you can no longer refer to it. Does this mean that the dynamic button is gone as well? No! The memory the AVM allocates for the button is still there, but you have no way of referring to it (or deleting it). It occupies memory until your session ends.

Likewise, you can lose your access to an object by resetting the handle. For example:

DEFINE VARIABLE hButton AS HANDLE NO-UNDO.
CREATE BUTTON hButton ASSIGN LABEL = "Lost Button!".
hButton = ?.

Oops! You reset your handle variable but the object is still there. You just cannot find it any more. Or consider this example:

DEFINE VARIABLE hButton AS HANDLE NO-UNDO.
DEFINE VARIABLE iCounter AS INTEGER NO-UNDO.
DO iCounter = 1 TO 10:
  CREATE BUTTON hButton ASSIGN LABEL = "Button #" + STRING(iCounter).
END.
MESSAGE hButton:LABEL.

The following figure shows the result.

Figure 1. Example button message

You just created ten buttons and lost contact with all but the last of them. This is not a good idea. Thus, the first rule of managing dynamic objects is to make sure that you do not lose track of them. Once you lose a valid handle to a dynamic object you cannot access it and it just sits in memory taking up space.

The next sections describe ways to manage memory and clean up dynamic objects so that this kind of memory leak does not happen in your application.