Compaq BASIC for OpenVMS
Alpha and VAX
The EXIT statement lets you exit from a main program, a SUB, FUNCTION,
or PICTURE subprogram, a multiline DEF, a statement block, or a handler.
- The DEF, FUNCTION, SUB, HANDLER, and PROGRAM keywords specify the
type of subprogram, multiline DEF, or handler from which BASIC
is to exit.
- If you specify an optional expression with the EXIT DEF statement
or with the EXIT FUNCTION statement, the expression becomes the
function result and supersedes any function assignment. It also
overrides any expression specified on the END DEF or END FUNCTION
statement. Note that the expression must be compatible with the
FUNCTION or DEF data type.
- Label specifies a statement label for an IF, SELECT, FOR,
WHILE, or UNTIL statement block.
- An EXIT SUB, EXIT FUNCTION, EXIT PROGRAM, EXIT DEF, or EXIT PICTURE
statement is equivalent to an unconditional branch to an equivalent END
statement. Control then passes to the statement that invoked the DEF or
to the statement following the statement that called the subprogram.
- The EXIT HANDLER statement causes BASIC to transfer control
to a specified area.
- If the current WHEN block is nested, control transfers to the
handler associated with the next outer protected region.
- If an ON ERROR statement is in effect and the current WHEN block is
not nested, control transfers to the target of the ON ERROR statement.
- If neither of the previous conditions is true, an EXIT HANDLER
statement transfers control to the calling program or DCL. This action
is the equivalent of the ON ERROR GO BACK statement.
- The EXIT PROGRAM statement causes BASIC to exit from a main
- An optional integer expression on an EXIT PROGRAM statement
specifies the exit status of the program that is reported to DCL.
- The expression specified by an EXIT PROGRAM statement overrides any
integer expression specified by an END PROGRAM statement.
- BASIC allows you to specify an EXIT PROGRAM statement
without a matching PROGRAM statement.
- The EXIT label statement is equivalent to an unconditional
branch to the first statement following the end of the IF, SELECT, FOR,
WHILE, or UNTIL statement labeled by the specified label.
- An EXIT FUNCTION, EXIT SUB or EXIT PROGRAM statement cannot be used
within a multiline DEF function.
- When the EXIT FUNCTION, EXIT SUB or EXIT PROGRAM statement
executes, BASIC releases all storage allocated to local
variables and returns control to the calling program.
IF A > 10
PRINT "OUT OF RANGE"
EXIT DEF 0
emp.bonus = A * 4
The EXP function returns the value of the mathematical constant
e raised to a specified power.
- The EXP function returns the value of e raised to the
power of real-exp.
- BASIC expects the argument of the EXP function to be a real
expression. When the argument is a real expression, BASIC
returns a value of the same floating-point size. When the argument is
not a real expression, BASIC converts the argument to the
default floating-point size and returns a value of the default
- When the default REAL size is SINGLE, DOUBLE, or SFLOAT, EXP allows
arguments from -88 to 88. If the default REAL size is GFLOAT or TFLOAT,
EXP allows arguments from -709 to 709. If the default REAL size is
HFLOAT or XFLOAT, the arguments can be in the range -11356 to 11355.
When the argument exceeds the upper limit of a range, BASIC
signals an error. When the argument is beyond the lower limit of a
range, the EXP function returns a zero and BASIC does not
signal an error.
DECLARE SINGLE num_val
num_val = EXP(4.6)
The EXTERNAL statement declares constants, variables, functions, and
subroutines external to your program. You can describe parameters for
external functions and subroutines.
- For external constants, data-type can be BYTE, WORD, LONG,
INTEGER (if default is not QUAD), SINGLE, SFLOAT, or REAL (if default
is SINGLE or SFLOAT).
- For external variables, the data type can be any valid
numeric data type.
- For external functions and subroutines, the data type can be BYTE,
WORD, LONG, QUAD, SINGLE, DOUBLE, GFLOAT, HFLOAT, SFLOAT, TFLOAT,
XFLOAT, DECIMAL, STRING, INTEGER, REAL, RFA, or a data type defined
with the RECORD statement. See Table 1-2 for more information about
data type size, range, and precision.
- The name of an external constant, variable, function, or subroutine
can be from 1 to 31 characters.
- For all external routine declarations, the name must be a valid
BASIC identifier and must not be the same as any other SUB,
FUNCTION, PICTURE, or PROGRAM name.
For more information about
external pictures, see Programming with VAX BASIC Graphics.
- Param-data-type specifies the data type of a parameter. If
you do not specify a data type, parameters are of the default data type
- Param-list is identical to external-param except
that no OPTIONAL parameter is allowed.
- Parameters in the param-list must agree in number and data
type with the parameters in the invocation. Param-data-type
includes ANY, BYTE, WORD, LONG, QUAD, INTEGER, SINGLE, DOUBLE, GFLOAT,
HFLOAT, SFLOAT, TFLOAT, XFLOAT, READ, a user-defined RECORD type,
STRING, or RFA.
- A maximum of 255 parameters may be passed.
- External Functions and Subroutines
- The data type that precedes the keyword FUNCTION defines the data
type of the function result.
- Pass-mech specifies how parameters are to be passed to the
function or subroutine.
- A pass-mech clause outside the parentheses applies to all
- A pass-mech clause inside the parentheses overrides the
previous pass-mech and applies only to the specific parameter.
- External-param defines the form of the arguments passed to
the external function or subprogram. Empty parentheses indicate that
the subprogram expects zero parameters. Missing parentheses indicate
that the EXTERNAL statement does not define parameters.
- Using ANY as a BASIC Data Type
- The ANY data type should only be used for calling non BASIC
procedures. Therefore, the ANY data type is illegal in a PICTURE
- If you specify ANY, BASIC does not perform data type
checking or conversions. If no passing mechanism is specified,
BASIC uses the default passing mechanism for the data type
passed in a given invocation.
- When you specify a data type, all following parameters that are not
specifically declared default to the last specified data type.
Similarly, when you specify ANY, all following unspecified parameters
default to the data type ANY until a new declaration is provided. For
EXTERNAL SUB allocate (LONG,ANY, )
- Passing Optional Parameters
- The OPTIONAL keyword should be used only for calling non BASIC
- If you specify the keyword OPTIONAL, BASIC treats all
following parameters as optional. In the following example, the last
three parameters are optional:
EXTERNAL SUB queue(STRING, OPTIONAL STRING, LONG, ANY)
- BASIC still performs type checking and conversion on
- If you want to omit an optional parameter that appears in the
middle of a parameter list, BASIC requires you to insert a
comma placeholder. However, if you want to omit an optional parameter
that appears at the end of a parameter list, you can omit that
parameter without inserting any placeholder.
- You can specify the keyword OPTIONAL only once in any one parameter
- Declaring Array Dimensions
The DIM keyword indicates that the
parameter is an array. Commas specify array dimensions. The number of
dimensions is equal to the number of commas plus 1. For example:
EXTERNAL STRING FUNCTION new (DOUBLE, STRING DIM(,), DIM( ))
This statement declares a function named new that has
three parameters. The first is a double-precision floating-point value,
the second is a two-dimensional string array, and the third is a
one-dimensional string array. The function returns a string result.
- The EXTERNAL statement must precede any program reference to the
constant, variable, function, subroutine or picture declared in the
- The EXTERNAL statement is not executable.
- A name declared in an EXTERNAL CONSTANT statement can be used in
any nondeclarative statement as if it were a constant.
- A name declared in an EXTERNAL FUNCTION statement can be used as a
function invocation in an expression. In addition, you can invoke a
function with the CALL statement unless the function data type is
DECIMAL, HFLOAT, or STRING.
- A name declared in an EXTERNAL SUB statement can be used in a CALL
- The optional pass-mech clauses in the EXTERNAL FUNCTION
and EXTERNAL SUB statements tell BASIC how to pass arguments to
a non BASIC function or subprogram.
- BY VALUE specifies that BASIC passes the argument's value.
- BY REF specifies that BASIC passes the argument's address.
This is the default for all arguments except strings and entire arrays.
If you know the size of string parameters and the dimensions of array
parameters, you can improve run-time performance by passing strings and
arrays by reference.
- BY DESC specifies that BASIC passes the address of a
BASIC descriptor. For information about the format of a
BASIC descriptor for strings and arrays, see Appendix A.
- If you do not specify the data type ANY or declare parameters as
optional, the arguments passed to external functions and subroutines
should match the external parameters declared in the EXTERNAL FUNCTION
or EXTERNAL SUB statement in number, type, and passing mechanism.
BASIC forces arguments to be compatible with declared
parameters. If they are not compatible, BASIC signals an error.
EXTERNAL LONG CONSTANT SS$_NORMAL
EXTERNAL WORD SYSNUM
EXTERNAL DOUBLE FUNCTION USR$2(WORD,LONG,ANY)
EXTERNAL SUB calc BY DESC (STRING DIM(,), BYTE BY REF)
The FIELD statement dynamically associates string variables with all or
parts of a record buffer. FIELD statements do not move data. Instead,
they permit direct access through string variables to sections of a
specified record buffer.
The FIELD statement is supported only for compatibility with
BASIC-PLUS-2. Because data defined in the FIELD statement can be
accessed only as string data, you must use the CVTxx functions
to process numeric data; therefore, you must convert string data to
numeric after you move it from the record buffer. Then, after
processing, you must convert numeric data back to string data before
transferring it to the record buffer. It is recommended that you use
the BASIC dynamic mapping feature or multiple maps instead of
the FIELD statement and CVTxx functions.
- Chnl-exp is a numeric expression that specifies a channel
number associated with a file. It must be immediately preceded by a
number sign (#). A file must be open on the specified channel or
BASIC signals an error.
- Int-exp specifies the number of characters in
str-var. However, a subsequent int-exp cannot depend
on the return string from a previous int-exp. For example, the
following statement is illegal because the second int-exp
depends on the return string A$:
FIELD #1%, 1% AS A$, ASCII(A$) AS B$
- A FIELD statement is executable. You can change a buffer
description at any time by executing another FIELD statement. For
FIELD #1%, 40% AS whole_field$
FIELD #1%, 10% AS A$, 10% AS B$, 10% AS C$, 10% AS D$
The first FIELD statement associates the first 40 characters of a
buffer with the variable whole_field$. The second FIELD
statement associates the first 10 characters of the same buffer with
A$, the second 10 characters with B$, and so on.
Later program statements can refer to any of the variables named in the
FIELD statements to access specific portions of the buffer.
- You cannot define virtual array strings as string variables in a
- A variable named in a FIELD statement cannot be used in a COMMON or
MAP statement, as a parameter in a CALL or SUB statement, or in a MOVE
- Attempting to access an element of a virtual array in a virtual
file that has associated FIELD variables, causes BASIC to signal
"Illegal operation" (ERR=141).
- If you name an array in a FIELD statement, you cannot use MAT
statements in the following format:
MAT array-name1 = array-name2
MAT array-name1 = NUL$
where array-name1 is named in a FIELD statement. This
causes BASIC to signal a compile-time error.
FIELD #8%, 2% AS U$, 2% AS CL$, 4% AS X$, 4% AS Y$
LSET U$ = CVT%$(U%)
LSET CL$ = CVT%$(CL%)
LSET X$ = CVTF$(X)
LSET Y$ = CVTF$(Y)
U% = CVT$%(U$)
CL% = CVT$%(CL$)
X = CVT$F(X$)
Y = CVT$F(Y$)
The FIND statement locates a specified record in a disk file and makes
it the current record for a GET, UPDATE, or DELETE operation. FIND
statements are valid on RMS sequential, relative, and indexed files.
- Chnl-exp is a numeric expression that specifies a channel
number associated with a file. It must be immediately preceded by a
number sign (#).
- If you specify a lock-clause, it must follow the
position-clause. If the lock-clause precedes the
position-clause, BASIC signals an error.
- If you specify the REGARDLESS lock-clause, you cannot
specify another lock-clause in the same FIND statement.
- Position-clause specifies the position of a record in a
file. BASIC signals an error if you specify a
position-clause and the channel is not associated with a disk
If you do not specify a position-clause, FIND locates records
sequentially. Sequential record access is valid on all files.
- The RFA position-clause allows you to randomly locate
records by specifying the record file address (RFA) of a record. You
specify the disk address of a record, and RMS locates the record at
that address. All file organizations can be accessed by RFA.
Rfa-exp in the RFA position-clause is a variable
of the RFA data type that specifies the record's file address. Note
that an RFA expression can only be a variable of the RFA data type or
the GETRFA function. Use the GETRFA function to find the RFA of a
- The RECORD position-clause allows you to randomly locate
records in relative and sequential fixed files by specifying the record
- Num-exp in the RECORD position-clause specifies
the number of the record you want to locate. It must be between 1 and
the number of the record with the highest number in the file.
- When you specify a RECORD clause, chnl-exp must be a
channel associated with an open relative or sequential fixed file.
- The KEY position-clause allows you to randomly locate
records in indexed files by specifying a key of reference, a relational
test, and a key value.
- An RFA value is valid only for the life of a specific version of a
file. If a new version of a file is created, the RFA values may change.
- Attempting to access a record with an invalid RFA value results in
a run-time error.
- Lock-clause allows you to control how a record is locked
to other access streams, to override lock checking when accessing
shared files that may contain locked records, or to specify what action
to take in the case of a locked record.
- The type of lock you impose on a record remains in effect until you
explicitly unlock it with a FREE or UNLOCK statement, until you close
the file, or until you perform a GET, FIND, UPDATE or DELETE on the
same channel (unless you specified UNLOCK EXPLICIT).
- The REGARDLESS lock-clause specifies that the FIND
statement can override lock checking and locate a record locked by
- When you specify a REGARDLESS lock-clause, BASIC
does not impose a lock on the retrieved record.
- The ALLOW lock-clause lets you control how a record is
locked to other users and access streams. The file associated with the
specified channel must have been opened with the UNLOCK EXPLICIT clause
or BASIC signals the error "Illegal record locking
- The ALLOW allow-clause can be one of the following:
- ALLOW NONE denies access to the record. This means that other
access streams cannot retrieve the record unless they bypass lock
checking with the GET REGARDLESS clause.
- ALLOW READ provides read access to the record. This means that
other access streams can retrieve the record but cannot use the DELETE
or UPDATE statements on the record.
- ALLOW MODIFY provides read and write to the record. This means that
other access streams can use the GET, FIND, DELETE, and UPDATE
statements on the record.
- If you do not open a file with the ACCESS READ clause or specify an
allow-clause, locking is imposed as follows:
- If the file associated with the specified channel was opened with
UNLOCK EXPLICIT, BASIC imposes the ALLOW NONE lock on the
retrieved record and the next GET or FIND operation does not unlock the
previously locked record.
- If the file associated with the specified channel was not opened
with UNLOCK EXPLICIT, BASIC locks the retrieved record and
unlocks the previously locked record.
- The WAIT lock-clause accepts an optional int-exp.
Int-exp represents a timeout value in seconds.
Int-exp must be from 0 through 255 or BASIC signals a
- WAIT followed by a timeout value causes RMS to wait for a locked
record for a given period of time.
- WAIT followed by no timeout value indicates that RMS should wait
indefinitely for the record to become available.
- If you specify a timeout value and the record does not become
available within that period, BASIC signals the run-time error
"Keyboard wait exhausted" (ERR=15). VMSSTATUS and RMSSTATUS
then return RMS$_TMO. For more information about the RMSSTATUS and
VMSSTATUS functions, see this chapter and the Compaq BASIC for OpenVMS Alpha and VAX Systems User Manual.
- If you attempt to wait for a record that another user has locked,
and consequently that user attempts to wait for the record you have
locked, a deadlock condition occurs. When a deadlock condition persists
for a period of time (as defined by the SYSGEN parameter
DEADLOCK_WAIT), RMS signals the error "RMS$_DEADLOCK" and
BASIC signals the error "Detected deadlock error while
waiting for GET or FIND" (ERR=193).
- If you specify a WAIT clause followed by a timeout value that is
less than the SYSGEN parameter DEADLOCK_WAIT, BASIC signals the
error "Keyboard wait exhausted" (ERR=15) even though a
deadlock condition may exist.
- In a key-clause, int-exp1 is the target key of
reference. It must be an integer in the range of zero to the
highest-numbered key for the file. The primary key is #0, the first
alternate key is #1, the second alternate key is #2, and so on.
Int-exp1 must be preceded by a number sign (#) or
BASIC signals an error.
- When you specify a key-clause, the specified channel must
be a channel associated with an open indexed file.
- Rel-op is a relational operator that specifies how
key-exp is to be compared with int-exp1 in the
- EQ means "equal to"
- NXEQ means "next or equal to"
- GE means "greater than or next" (a synonym for NXEQ)
- NX means "next"
- GT means "greater than" (a synonym for NX)
- A successful random FIND operation by key locates the first record
whose key satisfies the key-clause comparison:
- With an exact key match (EQ), a successful FIND locates the first
record in the file that equals the key value specified in
key-exp. However, if the characters specified by a
str-exp key expression are less than the key length,
characters specified by str-exp are matched approximately
rather than exactly. For example, if you specify ABC and the key length
is six characters, BASIC locates the first record that begins
with ABC. If you specify ABCABC, BASIC locates only a record
with the key ABCABC. If no match is possible, BASIC signals the
error "Record not found" (ERR=155).
- If you specify a next or equal to record key match (NXEQ), a
successful FIND locates the next record that equals the key length
specified in int-exp or str-exp. If no exact match
exists, BASIC locates the next record in the key sort order. If
the keys are in ascending order, the next record will have a greater
key value. If the keys are in descending order, the next record will
have a lesser key value.
- If you specify a greater than or equal to key match (GE), the
behavior is identical to that of next or equal to (NXEQ). (Likewise,
the behavior of GT is identical to NX.) However, the use of GE in a
descending key file may be confusing, because GE will retrieve the next
record in the key sort order, but the next record will have a lesser
key value. For this reason, it is recommended that you use NXEQ in new
program development, especially if you are using descending key files.
- If you specify a next key match (NX), a successful FIND locates the
first record that follows the relational operator in the sort order. If
no such record exists, BASIC signals the error "Record not
- Int-exp2 specifies an integer value to be compared with
the key value of a record.
- Str-exp specifies a string value to be compared with the
key value of a record. Str-exp can contain fewer characters
than the key of the record you want to locate, but cannot be a null
Str-exp cannot contain more characters than the
key of the record you want to locate. If str-exp does contain
more characters than the key, BASIC signals "Key size too large" (ERR =
- Decimal-exp in the key-clause specifies a packed
decimal value to be compared with the key value of a record.
- Quadword-exp in the key-clause specifies a record
or group exactly 8 bytes long to be compared with the key value of a
- The file on the specified channel must have been opened with ACCESS
MODIFY, ACCESS READ, or SCRATCH before your program can execute a FIND
- FIND does not transfer any data to the record buffer. To access the
contents of a record, use the GET statement.
- A successful sequential FIND operation updates both the current
record pointers and next record pointers.
- For sequential files, a successful FIND operation locates the next
sequential record (the record pointed to by the next record pointer) in
the file, changes the current record pointer to the record just found,
and the next record pointer to the next sequential record. If the
current record pointer points to the last record in a file, a
sequential FIND operation causes BASIC to signal "Record
not found" (ERR=155).
- For relative files, a successful FIND operation locates the record
that exists with the next higher record number (or cell number), makes
it the current record, and changes the next record pointer to the
current record pointer plus 1.
- For indexed files, a successful FIND operation locates the next
existing logical record in the current key of reference, makes this the
current record, and changes the next record pointer to the current
record pointer plus 1.
- A successful random access FIND operation by RFA or by record
changes the current record pointer to the record specified by
rfa-exp or int-exp, but leaves the next record
- A successful random access FIND operation by key changes the
current record pointer to the first record whose key satisfies the
key-clause comparison and leaves the next record pointer
- When a random access FIND operation by RFA, record, or key is not
successful, BASIC signals "Record not found"
(ERR=155). The values of the current record pointer and next record
pointer are undefined.
- You should not use a FIND statement on a terminal-format or virtual