[Access to Wang masthead]

Global Variables

Let your applications share information

From "VS Workshop",  Access to Wang, December 1992
  [ Prior Article ]     [ Return to the Catalog of articles ]     [ Next Article ]  

Just about any VS installation has need to pass small amounts of information between programs. Maybe you need to pass an alternate library or volume location or selections for a process; perhaps you need to provide a series of alternate libraries for program execution, as used in the simulation of the PATH concept featured last month in this space. Whatever the reason, Wang's Procedure language offers global variables to fill some of this need. This month we'll cover practical use of this feature and compare it with approaches offered by other operating environments.

Global variables defined

In Procedure, global variables are simply variables that retain their declaration and value outside of the immediate execution of the procedure. They must be used within procedures and are subject to some limitations in their use that, well, have prevented their global acceptance by programmers. In spite of these limitations, globals allow easy communication between procedures in a job stream. For example, perhaps you wish to define a variable in one procedure and use it in another, like this:


(...Begin procedure SETGLOB...)

     PROCEDURE SETGLOB - sets value of &GLOBVAR

     DECLARE &GLOBVAR GLOBAL STRING (1024)
        INITIAL "This is a test"

     RUN PROC2 IN DSBPROC ON SYSTEM

(...Begin procedure PROC2...)

     PROCEDURE PROC2 - used &GLOBVAR

     PROMPT CENTER &GLOBVAR (!,*)

     RETURN

(...End procedure PROC2...)

     RETURN

(...End procedure SETGLOB...)

In this example, SETGLOB declares the variable and assigns its initial value, then runs PROC2. PROC2 displays the non-blank contents of the variable on the screen, then returns to SETGLOB. Note that there is no declaration for &GLOBVAR in PROC2; global variables must be defined only once, and only at the lowest link level where they will be used. Furthermore, if a variable is declared that has the same name as a global variable, the global variable will not be available within that procedure or in any run by it; instead, the length and value will be set by the local procedure, reverting to the global values at the conclusion of the procedure.

The concept of link levels is important to understanding a critical drawback to global variables: the variable must be declared from a procedure and any subsequent access to this variable must be through programs run from that procedure. In practical terms, this means that the declaration is usually made in the user's start procedure - the first task executed after logon.

Despite the need to declare the variable at this lowest level, the value contained within that variable may be changed at any link level. For example, the variable could simply be declared in SETGLOB then set to a value in PROC2; on return to SETGLOB it could even be changed again. Standard Procedure language string manipulation logic may be used to add, change, or extract the value contained within.

Finally, note that there is no way to test the presence or absence of a global variable declaration. If a procedure incorrectly assumes that a variable has been declared globally and attempts to use it, an unrecoverable error will occur; there is no practical way to test for this condition prior to executing the statement in a procedure.

All in all, global variables must be declared consistently and used carefully. Their use is largely limited to communication of static information between processes.

Dynamic information assignment

To better meet read-world uses of globally-available information, I experimented with a technique for dynamically assigned variables, their labels, and the information contained within them. The result of these experiments is Procedure GLOBEXT, listed in Figure 1. The purpose of this subroutine is to extract the labels and data from a global variable and return them to a calling program or procedure. The variable names and values must be loaded into global variable &GLOBVAR in a format that resembles the statement below:


DECLARE &GLOBVAR GLOBAL STRING (1024) INITIAL
  "var1=Variable won;var2=Variable too;varlast=The end"

In this example there are three variable defined: var1, var2, and varlast. The contents of these variables would be defined by the string information beginning one character after the equals sign and ending with a semicolon. The arrangement is based loosely on the MS-DOS PATH statement, WIN.INI, and other data constructs from the PC world.

Two arguments must be passed to GLOBEXT: a label name (up to sixteen characters) and a receiver for the data (up to 64 characters). After accepting these two arguments from the calling program, GLOBEXT attempts to locate the keyword within &GLOBVAR by appending the equals sign and searching with the &INDEX function. If found, it declares the position after the equals sign to be the starting position of the data. The end position can either be the next semicolon located or the end of the string. String information between these two points becomes the value of the variable.

An experiment, GLOBEXT lacks some fault tolerance that should be written into production programs. As written, the routine is case-sensitive; a data label of 'var1' is not the same as 'Var1'. The routine will also consider blanks part of the data if placed after the equals sign and will not find the label if placed before the equals sign.

GLOBEXT in use

So what does this process buy you? A call to the subroutine from any program or procedure will tell you if the label exists (a return code of eight is sent back if not) and return the value if it does. This means that your programs can effectively test for the existence of data items and extract its value.

Figure 2 lists a test procedure that can be used to see the results of the subroutine. Assuming you have declared &GLOBVAR at an earlier link level and loaded the data shown above, a call for 'var1' as shown should display 'Variable won'. Changing the value of &KEYWORD to 'varbadname' will result in a return code of eight and no returned data.

Global information elsewhere

Facilities to pass global data are also available in other operating environments, notably UNIX and MS-DOS. I have more than a passing interest in these other systems; our shop uses both for our applications, in addition to MS Windows and the Wang OS. Beginning this month, I will compare and contrast some of the similarities in all of these operating environments to aid in better understanding of these popular environments.

In the PC world, environment variables can be set at command prompts or within programs, viewed using the SET command, and extracted and used within any program. Standard variables are defined for the command interpreter (COMSPEC), path, temp area, and the command prompt. User- declared variables cannot be extracted from a command line; they must be interpreted by the command processor (COMMAND.COM) or used within programs.

UNIX uses named parameters (a.k.a. shell variables), which are declared or displayed with the SET command, like MS-DOS. Variables are available only at that link level unless the EXPORT command is included to allow them to become available at other levels. There are many standard variables, including those that are used by system utilities to accommodate differences in terminals, preferences, keyboards, etc. Sophisticated use of shell variables depends on the shell selected for that user; most UNIX environments offer at least two of the three most popular command interpreters, and their usage differs markedly.

There you have it: a few ways to share a little data between applications. Let me know how your global travels go.


Figure 1: Procedure GLOBEXT


PROCEDURE GLOBEXT

* Extracts values from &GLOBVAR using the
* &INDEX function of Procedure language

USING &KEYNAME    STRING (16),
      &KEYVALUE   STRING (64)

DECLARE &VAR, &START, &LEN INTEGER
ASSIGN &KEYVALUE = " "

ASSIGN &VAR
   = &INDEX (&GLOBVAR, &KEYNAME (1,*) !! "=")

IF &VAR = 0      RETURN CODE = 8

ASSIGN &START
   = &INDEX (&GLOBVAR (&VAR, *), "=") + 1

ASSIGN &LEN
   = &INDEX (&GLOBVAR (&VAR, *), ";") - &START

IF &LEN <= 0    [ end character not found ]
   ASSIGN &LEN
      = &LENGTH (&GLOBVAR (1,*))
      - (&START + &VAR) + 2

ASSIGN &KEYVALUE
   = &GLOBVAR (&VAR + &START - 1, &LEN)

RETURN

Figure 2: Procedure GTEST


PROCEDURE GTEST - tests global procedure extract program

DECLARE &KEYWORD   STRING (16)
DECLARE &VAL       STRING (64)
DECLARE &RC        INTEGER

ASSIGN &KEYWORD = "var1"

RUN GLOBEXT [ in LIBRARY on VOLUME ]
    USING &KEYWORD, &VAL
ASSIGN &RC      = @RUN

PROMPT CENTER "Keyword =", LINE &KEYWORD (1,*);;
       CENTER "Returned value =", LINE &VAL (1.*)
       CENTER "Return code = ", &RC;;

RETURN

  [ Prior Article ]     [ Return to the Catalog of articles ]     [ Next Article ]  


Copyright © 1992 Dennis S. Barnes
Reprints of this article are permitted without notification if the source of the information is clearly identified