[an error occurred while processing this directive]
HP OpenVMS Systems Documentation |
HP Pascal for OpenVMS
|
Previous | Contents | Index |
Assignment compatibility rules apply to the types of values used to initialize variables, the types of expressions assigned to variables with the assignment operator (:=), and the types of actual parameters passed to formal value parameters. A variable or formal parameter is always compatible with expressions of its type.
Table 2-11 shows the contexts in which the type of an expression is assignment compatible with the type of a variable or a formal parameter when the types are not the same.
Type of Variable | Type of Assignment-Compatible Expression or Parameter |
---|---|
INTEGER | INTEGER, UNSIGNED, INTEGER64, UNSIGNED64 |
UNSIGNED | INTEGER, UNSIGNED, INTEGER64, UNSIGNED64 |
INTEGER64 | INTEGER, UNSIGNED, INTEGER64, UNSIGNED64 |
UNSIGNED64 | INTEGER, UNSIGNED, INTEGER64, UNSIGNED64 |
Subrange | Base type of the subrange |
REAL, SINGLE | REAL, SINGLE, UNSIGNED, INTEGER, INTEGER64, UNSIGNED64 |
DOUBLE | DOUBLE, REAL, SINGLE, UNSIGNED, INTEGER, INTEGER64, UNSIGNED64 |
QUADRUPLE | QUADRUPLE, DOUBLE, REAL, SINGLE, UNSIGNED, INTEGER |
PACKED ARRAY OF
CHAR |
CHAR, unpacked array of CHAR, PACKED ARRAY OF CHAR with the same or smaller length, VARYING string whose current length is equal to or less than the packed array |
VARYING OF CHAR | CHAR, unpacked array of CHAR, PACKED ARRAY OF CHAR, VARYING, STRING, string whose current value does not exceed the maximum length of the variable or parameter |
STRING | CHAR, unpacked array of CHAR, PACKED ARRAY OF CHAR, VARYING, STRING, string whose current value does not exceed the maximum length of the variable or parameter |
Pointer | Pointer to a structurally compatible type |
Two record types or two array types are assignment compatible if they are structurally compatible.
When you assign one record variable to another, or one array variable to another, the HP Pascal compiler does not check for out-of-range assignments to record fields or array components; such assignments do not result in an error message, even if subrange checking is enabled at compile time.A set expression is assignment compatible with a set variable if the set's base types are compatible. In addition, all elements of the set expression must be included in the range of the variable's base type.
Note that assignment operations are not allowed on objects of file types or structured types that have file components.
Two discriminated schema types are assignment compatible if they are of the same type family and if their actual discriminant values are identical. A dereferenced pointer to an undiscriminated schema type is actually referencing a discriminated schema object whose discriminants were specified in a call to the NEW function. Although STRING is a schema, the rules in Table 2-11 take precedence.
The declaration section contains declarations or definitions of constants, labels, user-defined data types, variables, and user-defined functions and procedures. In addition, only modules can contain initialization and finalization sections. Each appears in a subsection introduced by Pascal reserved words.
This chapter discusses the following topics:
These sections appear after the header and before the executable section (if any). The TO BEGIN DO and TO END DO sections can appear only in modules and only once within a module.
The remaining sections can appear in programs, modules, functions, or procedures; they can appear more than once and in any order in a single declaration section. If you use one kind of section more than once in a declaration section, be sure to declare types, variables, and constants before you use them in subsequent sections.
The CONST section defines symbolic constants by associating identifiers with compile-time expressions; it has the following form:
CONST {constant-identifier = constant-expression};... |
constant-identifier
The identifier of the symbolic constant being defined.constant-expression
Any legal compile-time expression.
Once a constant identifier is associated with an expression, the identifier retains the value of that expression throughout the scope in which it was declared. You can change the value only by changing the definition in the CONST section.
Consider the following example:
TYPE array_type1 = ARRAY[1..10] OF INTEGER; CONST Year = 1984; Tiny = 1.7253; Month = 'November'; Initial = 'P'; Lie = FALSE; Untruth = Lie; Almost_Pi = 22.0/7.0; array_const = array_type1[1..3,5 : 1; 4,6 : 2; 7..9 : 3; 10 : 7]; |
A label is a tag that makes an executable statement accessible to a GOTO statement. The LABEL section declares labels and has the following form:
LABEL {label},...; |
label
A decimal integer between 0 and 9999 (as an extension, between 0 and MAXINT), or a symbolic name. When declaring several labels, you can specify them in any order. The declaration and the occurrence of the label must be at the same level in the program.
A label can appear only once within the scope of the label declaration. It can precede any executable statement in the program. Use a colon (:) to separate the label from the statement it precedes. Labels can be accessed only by GOTO statements.
Consider the following example:
LABEL marker, 5; {In the executable section: } IF a <= 150 THEN GOTO 5 ELSE GOTO marker ; . . . 5: a := a + 1; . . . marker: WHILE x < 20 DO {Statement...} |
The TO BEGIN DO section allows you to specify a statement, in a module that is to be executed before the executable section of the main program; it has the following form:
TO BEGIN DO statement; |
statement
A Pascal statement.
The TO BEGIN DO section can only appear in modules, can only appear once in a module, and must appear as the last section in the declaration section. (If appearing together, the TO BEGIN DO section must precede the TO END DO section at the end of the declaration section.)
Consider the following example:
MODULE x( INPUT, OUTPUT ); VAR Debug : BOOLEAN; PROCEDURE Test(...); {Executable section...} TO BEGIN DO BEGIN WRITE('Debug Module x? '); READLN( Debug ); END; END. |
As a general rule, if a program or module inherits an environment file, the compiler executes the initialization section in the inherited module before the initialization section in the program or module that inherited it. If a module or program inherits more than one module that contains an initialization section, the order of execution of the inherited modules is undefined.
Consider the following example:
[ENVIRONMENT( 'Mod1' )] MODULE Mod1; VAR i : INTEGER; TO BEGIN DO i := 5; {In a separate compilation unit:} [INHERIT( 'Mod1' )] MODULE Mod2; VAR j : INTEGER; TO BEGIN DO j := i + 1; {First execute code in Mod1 for correct results} |
Figure 3-1 shows the order of execution of initialization and finalization sections. Each circle is a module that contains both a TO BEGIN DO and a TO END DO section, and each arrow indicates the order of inheritance for the environment files.
Figure 3-1 Order of Execution for TO BEGIN DO and TO END DO Sections
The execution order for initialization and finalization sections in Modules 2 and 3 cannot be determined. The headers for the modules in Figure 3-1 are as follows:
[ENVIRONMENT] MODULE Mod1; ... [ENVIRONMENT, INHERIT( 'Mod1' )] MODULE Mod2; ... [ENVIRONMENT, INHERIT(' Mod1' )] MODULE Mod3; ... [INHERIT( 'Mod2', 'Mod3' )] MODULE Mod4; ... |
The name of the compiler-generated initialization routine is formed by taking the module name and appending %INIT . If you wish to provide a different name, you can use the [GLOBAL] attribute on the top of the module to specify a different name. For example:
[ENVIRONMENT,GLOBAL(MYINIT)] MODULE Mod1; ... |
This alternate name is encoded in the resulting environment file so all modules that inherit this environment will automatically call the initializaton routine by its new alternate name.
The TO END DO section allows you to specify a statement in a module that is to be executed after the executable section of the main program; it has the following form:
TO END DO statement; |
statement
A Pascal statement.
The TO END DO section can only appear in modules, can only appear once
in a module, and must appear as the last section in the declaration
section. (If appearing together, the TO END DO section must come after
the TO BEGIN DO section at the end of the declaration section.)
As a general rule, if a compilation unit inherits an environment file,
the finalization section in the inheriting compilation unit must be
executed before the finalization section in the inherited compilation
unit. Also, if more than one module with a finalization section
inherits a single module, the order of finalization of the inheriting
modules cannot be determined. Figure 3-1 shows an example of the
order of execution of TO END DO sections.
The compiler implements a TO END DO section by creating an invisible TO
BEGIN DO section if TO BEGIN DO wasn't used or by augmenting an
existing TO BEGIN DO section with a call to the Pascal Run-Time Library
to register the finalization routine.
Here is an example using both TO BEGIN DO and TO END DO:
MODULE File_Output; VAR Out_File : TEXT; t : TIMESTAMP; PROCEDURE Test(...); {Executable section...} TO BEGIN DO OPEN( Out_File, 'foo.dat' ); TO END DO BEGIN GETTIMESTAMP( t ); WRITELN( 'foo.dat closed at', TIME( t ) ); CLOSE( Out_File ) END; END. |
The TYPE section introduces the name and set of values for a user-defined type or schema declaration.
It has the following form:
[[type-attribute-list]] TYPE {type-identifier = [[attribute-list]] type-denoter } { {schema-declaration } { } [[VALUE initial-state-specifier]]};... |
One or more attributes that apply to the entire TYPE section. Only the ALIGN, ENUMERATION_SIZE, or HIDDEN attributes can be specified here.type-attribute-list
The following rules apply to the use of initial-state-specifiers on data types:
This example declares variables of user-defined types. Note that in the declaration of variable week5, the VALUE Sun overrides the initial state specified in the TYPE declaration by VALUE Mon.
TYPE Days_of_Week = ( Sun, Mon, Tues, Wed, Thurs, Fri, Sat ) VALUE Mon; Array_Template( Upper_Bound : INTEGER ) = ARRAY [1..Upper_Bound] OF INTEGER; VAR {Declaring variables of user-defined types:} week1, week2, week3, week4 : Days_of_Week; {Initial value: Mon} week5 : Days_of_Week VALUE Sun; {Initial value: Sun} array_type2 : array_template( x ); {x is a run-time expression} |
HP Pascal requires that all user-defined type identifiers (except base types of pointers) be defined before they are used in the definitions of other types. A base type must be defined before the end of the TYPE section in which it is first mentioned, as shown in the this example:
TYPE Ptr_to_Movie = ^Movie; {Movie is defined later} Name = PACKED ARRAY[1..20] OF CHAR; {Defined before used} Movie = RECORD Title, Director : Name; Year : INTEGER; Stars : FILE OF Name; Next : Ptr_to_Movie; END; |
If you choose, you can use the VALUE section as an HP Pascal extension that initializes ordinal, real, array, record, set, and string variables. (If you require portable code, use the VALUE reserved word in either TYPE definitions or VAR declarations.) The exact format of an initialization depends on the type of the variable being initialized. The VALUE section has the following form:
VALUE {variable-identifier := constant-expression};... |
The name of the variable to be initialized. You cannot specify a list of variable identifiers. You can initialize a variable or variable component only once in the VALUE section. Any variables appearing in the VALUE section must appear in a previous VAR section.variable-identifier
Unlike other declaration sections, the VALUE section can appear only in a program or module declaration section. You cannot use the VALUE declaration section in procedures or functions. If you wish to initialize variables in procedures and functions, use an initial-state specifier (by using the VALUE reserved word in either the TYPE or VAR section).
You can assign values to complete structured variables or to a single component of that variable.
The VAR section declares variables and associates each variable with an identifier, a type, and an optional initial value.
It has the following form:
[[var-attribute-list]] VAR {{variable-identifier},... : [[attribute-list]] type-denoter {:= } [[ {VALUE } initial-state-specifier ]] };... |
One or more attributes that apply to the entire VAR section. Only the ALIGN, ENUMERATION_SIZE or HIDDEN attributes can be specified here.var-attribute-list
You can combine several identifiers in the same variable declaration if the variables are of the same type and are being initialized either with the same value or not at all.
Consider the following example:
TYPE Hours_Worked = ARRAY[1..10] OF INTEGER; VAR Answer, Rumor : BOOLEAN; Temp : INTEGER VALUE 60; Grade : 'A'..'D'; Weekly_Hours : Hours_Worked VALUE [1..3 : 7; OTHERWISE 5]; |
The following rules apply to the use of initial-state specifiers on variables:
A reference to a variable consists of the variable's use in one of the following situations:
The existence of a variable reference sometimes prohibits certain operations from being performed on the variable. Such restrictions are noted throughout this manual.
Previous | Next | Contents | Index |