Executing Other Maintain Procedures

In this section:

You can call one Maintain procedure from another with the CALL command. (Maintain procedure here means any procedure of Maintain language commands.) CALL simplifies the process of modularizing an application; software designed as a group of related modules tends to be easier to debug, easier to maintain, and lends itself to being reused by other applications—all of which increase your productivity.

CALL also makes it easy to partition an application, deploying each type of logic on the platform on which it will run most effectively.

The following diagram illustrates how to describe the relationship between called and calling procedures. It describes a sequence of five procedures from the perspective of the middle procedure, C FOCEXEC. (Note that a root procedure is also called the starting procedure.)


Top of page

Example: Calling Another Maintain Procedure

Consider the EMPUPDAT procedure:

MAINTAIN FILE Employee
FOR ALL NEXT Emp_ID INTO EmpStack;
.
.
.
CALL NewClass; 
.
.
.
END

This calls the NEWCLASS procedure:

MAINTAIN
.
.
.
END

In this example, EMPUPDAT is the parent procedure and NEWCLASS is the child procedure. When the child procedure—and any procedures that it, in turn, has invoked—has finished running, control returns to the parent.


Top of page

x
Passing Variables Between Procedures

All user variables (both stacks and simple, or scalar, variables) are local to a procedure, not global to the application. In other words, to protect them from unintended changes in other parts of an application, you cannot directly refer to a variable outside of the procedure in which it is found (with the exception of the FocError, FocErrorRow, FocFetch, and FocCurrent transaction variables). However, you can access a variable's data in other procedures, simply by passing it as an argument from one procedure to another.

To pass variables as arguments, you only need to name them in the CALL command, and then again in the corresponding MAINTAIN command. Some variable attributes must match in the CALL and MAINTAIN commands:

Other attributes need not match:

Once you have passed a variable to a child procedure, you must define it in that procedure. How you define it depends upon the type of variable:

Once a variable has been defined in the child procedure, its data becomes available. If you refer to stack cells that were not assigned values in the parent procedure, they are assigned default values (such as spaces or zeros) in the child procedure, and Maintain displays a message warning that they have not been explicitly assigned any values.

When the child procedure returns control back to the parent procedure, the values of stacks and simple variables specified as INTO variables are passed back to the parent. The values of stacks and simple variables specified only as FROM variables are not passed back.



Example: Passing Data Between Maintain Procedures

For example, this procedure,

MAINTAIN FILE Employee
FOR ALL NEXT Emp_ID INTO EmpStack;
.
.
.
CALL NewClass FROM EmpStack CourseStack INTO CourseStack;
.
.
.
END

calls the NEWCLASS procedure:

MAINTAIN FROM StudentStack CourseStack INTO CourseStack
.
.
.
END

EmpStack and CourseStack in the parent procedure correspond to StudentStack and CourseStack in the child procedure.


Top of page

x
Accessing Data Sources in the Child Procedure

If a child procedure accesses a data source, whether retrieving or writing records, you must specify the data source in the MAINTAIN command. This is done the same way as for a stand-alone procedure. For example:

MAINTAIN FILES Employee AND EducFile FROM StuStk INTO CoursStk
.
.
.
END

Top of page

x
Data Source Position

Each Maintain procedure tracks its own position in the data source. When you first call a procedure, Maintain positions you at the beginning of each segment in each data source accessed within that procedure; after navigating through a data source, you can reposition to the beginning of a segment by issuing the REPOSITION command. Each procedure's data source positions are independent of the positions established in other procedures.

When a child procedure returns control to its parent, by default it clears its data source positions. You can specify that it retain its positions for future calls by using the KEEP option, as described in the Optimizing Performance: Data Continuity and Memory Management.


Top of page

x
Optimizing Performance: Data Continuity and Memory Management

By default, when you terminate a child procedure, Maintain clears its data from memory to save space. You can optimize your application's performance by specifying, each time you terminate a child procedure, how you want Maintain to handle the procedure's data. You have two options, based on how often you will call a given procedure over the course of an application:

For more information about transactions spanning procedures, see Designing Transactions That Span Procedures.

You can specify how a procedure will handle its data in memory by terminating it with the GOTO END command qualified with the appropriate memory-management phrase. The syntax is

GOTO END [KEEP|RESET];

where:

KEEP

Terminates the procedure, but keeps its data—the values of its variables and data source position pointers—in memory. It remains in memory through the next invocation, or (if it is not called again) until the application terminates. The procedure does not issue an implied COMMIT command to close an open logical transaction.

RESET

Terminates the procedure, clears its data from memory, and issues an implied COMMIT command to close an open logical transaction. This is the default.

You can use both options in the same procedure. For example, when you are ready to end a child procedure, you could evaluate what logic the procedure will need to perform when it is next called and then branch accordingly either to keep data in memory, saving time and providing data continuity, or to clear data from memory to conserve space.


Information Builders