| Front Page | News Headlines | Technical Headlines | Planning Features | Advanced Search |
Acucorp Sponsor Message

April 2003

Boosting Your e3000 Productivity

Quick and Dirty Solutions with CI Programming

By Ken Robertson

An overworked, understaffed data processing department is all too common in today’s ever belt-tightening, down-sizing and de-staffing companies.

An ad-hoc request may come to the harried data processing manager. She may throw her hands up in despair and say, “It can’t be done. Not within the time frame that you need it in.” Of course, every computer-literate person knows deep down in his heart that every programming request can be fulfilled, if the programmer has enough hours to code, debug, test, document and implement the new program. The informed DP manager knows that programming the Command Interpreter (CI) can sometimes reduce that time, changing the “impossible deadline” into something more achievable.

Getting Data Into and Out of Files

So you want to keep some data around for a while? Use a file! Well, you knew that already, I’ll bet. What you probably didn’t know is that you can get data into and out of files fairly easily, using IO re-direction and the print command. IO re-direction allows input or output to be directed to a file instead of to your terminal. IO re-direction uses the symbols ">", ">>" and "<". Use ">" to re-direct output to a temporary file. (You can make the file permanent if you use a file command.) Use ">>" to append output to the file. Finally, use "<" to re-direct input from a file:

echo Value 96 > myfile
echo This is the second line >> myfile
input my_var < myfile
setvar mynum_var str("!my_var",7,2)
setvar mynum_var_2 !mynum_var - (6 * 9 )
echo The answer to the meaning of life, the universe
echo and everything is !mynum_var_2.

After executing the above command file, the file Myfile will contain two lines, “Value 42” and “This is the second line.” (Without quotes, of course.) The Input command uses IO re-direction to read the first record of the file, and assigns the value to the variable my_var. The first Setvar extracts the number from the middle of the string, and proceeds to use the value in an important calculation in the next line.

How can you assign the data in the second and consequent lines of a file to variables? You use the Print command to select the record that you want from the file, sending the output to a new file:

print myfile;start=2;end=2 > myfile2

You can then use the Input command to extract the string from the second file.

Rolling Your Own System Variables

It’s easy enough to create a static file of Setvar commands that gets invoked at logon time, and it’s not difficult to modify the file programmatically. For example, let’s say that you would like to remember a particular variable from session to session, such as the name of your favorite printer. You can name the file that contains the Setvars, Mygvars. It will contain the line: setvar my_printer “biglaser”

The value of this variable may change during your session, but you may want to keep it for the next time that you log on. To do this, you must replace your normal logoff procedure (the Bye or Exit command) with a command file that saves the variable in a file, and then logs you off.

purge mygvars > $null
file mygvars;save
echo setvar my_printer "!my_printer" > *mygvars

Whenever you type byebye, the setvar command is written to Mygvars and you are then logged off. The default close disposition of an IO re-direction file is TEMP, which is why you have to specify a file equation. Because you are never certain that this file exists beforehand, doing a Purge ensures that it does not.

Program Control — If/Else and While

One of the reasons we like programming the CI is its lack of goto’s. Consider the following:

echo Powers of 2...
if "!hpjobname" = "KARNAK" then
setvar loop_count 1
setvar temp 1
while !loop_count < 10 do
setvar temp !temp * 2
echo 2^!loop_count = !temp
setvar loop_count !loop_count + 1
echo Sorry, you’re not authorized to know.

The above command file will display a “powers of two” table from one though nine for the user who is logged on as KARNAK. You can indent code inside If and While blocks for readability, because the CI doesn’t care about leading spaces or blank lines. However, you must use the Comment command to insert comments.

There are times when you wish to exit out of a loop in an ungraceful manner. To do this, use the Return command. We often use this when we display help in a command file, and we don’t want to clutter further code with a big if/endif block:

parm hidden_away="?"
if "!hidden_away" = "?" then
echo This command file doesn’t do much,
echo but it does it well.
echo Local variable is !hidden_away.

Another way to terminate loops and nested command files is to use the escape command. This command will blow you right back to the CI. (Using the Return command only exits the current command file.) You can optionally set the CIERROR jcw by adding a value to the end of the Escape command: escape 007

Simulating Arrays

It’s true — arrays are not directly supported in the CI. However, because of some undocumented techniques (read: tricks), you can simulate arrays. One question that may immediately pop into your head is “Why would I want to use arrays?” Arrays are useful for table driven events, such as returning days per month, sessions on ldevs, etc. We won’t keep you in suspense. Here’s the core method:

setvar !variable_name!variable_index value

By using the expression evaluation feature of the CI, you can have a changeable variable name in the Setvar command. CAVEAT USER: This only works within command files! If you try to do this interactively, the expression evaluation on the Setvar command is performed for the part of the command line after the variable name. Within a command file, the entire line is evaluated before being passed to the CI for re-evaluation.

In much the same way, you can use command files to change sequences of commands, i.e., to create self-modifying code. For example:

setvar variable_command "setvar apple ""orange"""

If you run the command file, and then display the contents of the variable, you will see:

weirdcmd {execute command file, above}
showvar apple
APPLE = orange

To simulate arrays, you must assign a variable per each element. For example, you would assign months_12 for months(12). This variable can be either string or numeric, but keep in mind that string variables can be up to 256 characters long.

Here are a few command files that allow you to manipulate arrays.

parm array_name nbr_elements=0 initial_value=0
setvar array_index 0
while !array_index <= !nbr_elements do
setvar !array_name!array_index !initial_value
setvar array_index array_index + 1

The command file Arraydef allocates variables for each element of the array that you need. The call sequence would be something like arraydef months_ 12

Just as you put an index in parentheses, we like to put underbars at the end of array names so that they are more readable.

There is a limit on the storage (it was about 20K bytes in MPE/iX 5.0). The space used can be calculated by adding the number of characters in each variable name, plus 4 bytes per integer item, or the length of each string. For example, the integer variable XYZZY takes up 5 bytes for the name, and four more bytes for its integer value. When you run out of space, you get the following error from the CI:

Symbol table full: addition failed. To continue, delete some variables, or start a new session. (CIERR 8122).

The following command file allows you to return the space used by your pseudo-array when you are finished using it:

parm array_name nbr_elements=0
setvar array_index 0
while !array_index < !nbr_elements do
deletevar !array_name!array_index
setvar array_index array_index + 1

To demonstrate how arrays can be set (and values returned), the following two command files, Arrayset and Arrayget, use the expression evaluation feature of the CI to convert the element number to the actual variable name. Setvar is called to set either the value, or the name of the variable passed to the command file:

parm array_name element_nbr=0
anyparm set_value
setvar !array_name!element_nbr !setvalue

parm destination_var array_name element_nbr=0
anyparm get_value
setvar !destination_var !array_name!element_nbr

Here’s a quick command file to show how you can use arrays in a month table. It uses the Input command to prompt the user for the number of days for each month.

setvar months_nbr 0
while !months_nbr < 12 do
setvar months_nbr months_nbr + 1
input months_!months_nbr; &
prompt="Enter the number of days in month
!months_nbr: "
deletevar months_nbr

For more on CI programming, read www.robelle.com/ftp/papers/progci.txt


Copyright The 3000 NewsWire. All rights reserved.