HP 3000 Manuals

Predefined Routines [ HP Pascal/iX Reference Manual ] MPE/iX 5.0 Documentation


HP Pascal/iX Reference Manual

Predefined Routines 

The system programming extensions define the following additional
predefined procedures and functions.

Addressing and Pointers 

Addr.   

The predefined function addr allows the user to create references to
routines or data.

Usage 

     addr(variable) 
     addr(variable,offset) 
     addr(routine-name) 

Parameters 

variable              A variable or reference parameter, or a component
                      of an unpacked structured variable or reference
                      parameter.  You can take the address of a component
                      of a packed or crunched structure, if the component
                      begins on a byte-aligned boundary.

offset                A signed integer expression.

routine-name          The name of a procedure or function.

Description 

The predefined function addr returns a pointer value that is the address
of the argument.  The type of the pointer returned by addr is assignment
compatible with any pointer type.  Addr returns a short or long pointer 
depending on the context in which it is called, the context being the
type of the target variable of an assignment, the type of a formal
parameter, or the target type of a type coercion.

If the type coercion target type is not a pointer type, addr returns a
globalanypointer.

If an integer argument is supplied, the pointer returned is offset by the
integer number of bytes from the original variable whose address was
taken.

It is illegal to take the address of a formal value or READONLY
parameter.

It is illegal to take the address of a component of a PACKED or CRUNCHED
structure, if the component does not begin on a byte-aligned boundary.

If addr is called with the name of a procedure or function, the value
returned is a reference to that procedure or function.  The function
result type is assignment compatible with a PROCEDURE or FUNCTION type
whose parameter list is congruent with the parameter list of the routine
passed to addr.

If the name passed to addr cannot be resolved, the value NIL is returned.

Example 

     $STANDARD_LEVEL 'HP_MODCAL', TYPE_COERCION 'CONVERSION'$
     TYPE
        p_to_p_type = ^ p_to_p_type;

     VAR
        p_to_p : p_to_p_type;

     BEGIN
        p_to_p := addr( p_to_p );
        p_to_p := p_to_p_type( addr( p_to_p^, sizeof( p_to_p^ ) ) )^;
     END

The first assignment points the pointer p_to_p to itself.  The second
assignment takes the address of the data referenced by p_to_p (which is
itself), offset by the size of the data that p_to_p points to, treats the
value at that location as a pointer, and assigns the value pointed to by
that pointer back to p_to_p.

Addtopointer.   

The predefined function addtopointer allows the user to perform address
arithmetic with pointers.

Usage 

     addtopointer(pointer, delta) 

Parameters 

pointer               A pointer expression.

delta                 A signed integer expression whose range restriction
                      is implementation dependent.

Description 

Addtopointer returns a pointer value that points delta bytes away from
where the argument pointer pointed.  The type of the pointer returned by
addtopointer is the same as the type of the parameter pointer.

The results of an overflow are implementation dependent.

Example 

     TYPE
        intptr = ^integer;

     VAR
        ptr1: intptr;
        ptr2: intptr;
        i:    integer;

     BEGIN
        ptr2 := addtopointer (ptr1, i);
        ptr1 := addtopointer (ptr1, sizeof(integer));
     END

Buildpointer.   

The predefined function buildpointer allows the user to construct pointer
values.

Usage 

     buildpointer(space,offset) 

Parameters 

space                 A space identifier whose range restriction and
                      semantics are implementation dependent.

offset                A bit32 expression whose range restriction is
                      implementation dependent.

Description 

buildpointer returns a pointer of type globalanyptr whose value is the
address offset bytes into space.

Example 

     CONST
        Global_Known_Space = 4916;

     VAR
        Ptr1 : GlobalAnyPtr;
        Ptr2 : GlobalAnyPtr;
        SID  : Integer;
        Off  : Integer;

     BEGIN
     Ptr1 := BuildPointer (Global_Known_Space, 0);
     off := 4;
     Ptr2 := BuildPointer (SID, Off);
     END.

In the above example, the constant Global_Known_Space represents the
value of a known space.

The first use of buildpointer creates a pointer to the location with an
offset of zero in the space whose space id is Global_Known_Space.

The second use of buildpointer creates a pointer to the location four
bytes from the beginning of the space whose space has been assigned to
the variable SID.

Move Routines 

The system programming extensions provide the predefined procedures
move_l_to_r, move_r_to_l, fast_fill, and move_fast for generalized and
efficient data copying.

Move_L_to_R.   

The predefined procedure move_l_to_r provides a generalized array copying
mechanism.

Usage 

     move_l_to_r(count,source,source_index,target,target_index) 

Parameters 

count                 A positive integer expression whose value is the
                      number of elements to move.

source                The source array from where elements will be moved.

source_index          An integer expression whose value is the index into
                      the source array of the leftmost element to be
                      moved.  The value must be greater than or equal to
                      the index of the first element in the source array,
                      and less than or equal to the index of the last
                      element in the source array minus the move count.

target                The target array to where elements are moved.

target_index          An integer expression whose value is the index into
                      the target array to where the move begins.  The
                      value must be greater than or equal to the index of
                      the first element in the target array, and less
                      than or equal to the index of the last element in
                      the target array minus the move count.

Description 

The syntax of the procedure is identical to the syntax of the predefined
procedure strmove.

move_l_to_r moves elements from left to right.  In a left to right move,
the first element to be moved is the left-most (lowest indexed) element,
and the last element to be moved is the right-most (highest indexed)
element.

Even if the elements of the array to be moved are arrays themselves, the
array will be moved as a single item.

The following diagram shows the order of copying elements for
move_l_to_r.

	       Click here to view figure.
          Figure 11-6.  Copying Order for move_l_to_r 

Example 

     TYPE
        Index_Type_1 =  0..20;
        Index_Type_2 = -3..17;

        Array_Type_1 = PACKED ARRAY [Index_Type_1] of SHORTINT;
        Array_Type_2 = ARRAY [Index_Type_2] of SHORTINT;

     VAR
        Array_1 = Array_Type_1;
        Array_2 = Array_Type_2;
        Index   = Integer;

     BEGIN

        Move_L_to_R ( 5, Array_1, 3,  Array_2, -3 )

        {  is equivalent to:  }

        FOR Index := 0 TO 4 DO

           Array_2[Index-3] := Array_1[3+Index]

        {  is equivalent to:  }

        Array_2[-3] := Array_1[3]
        Array_2[-2] := Array_1[4]
        Array_2[-1] := Array_1[5]
        Array_2[0]  := Array_1[6]
        Array_2[1]  := Array_1[7]

Move_R_to_L.   

The predefined procedure move_r_to_l provides a generalized array copying
mechanism.

Usage 

     move_r_to_l(count,source,source_index,target,target_index) 

Parameters 

count                 A positive integer expression whose value is the
                      number of elements to move.

source                The source array from where elements will be moved.

source_index          An integer expression whose value is the index into
                      the source array from where the move will begin.
                      The value must be greater than or equal to the
                      index of the first element in the source array, and
                      less than or equal to the index of the last element
                      in the source array minus the move count.

target                The target array to where elements will be moved.

target_index          An integer expression whose value is the index into
                      the target array to where the move will begin.  The
                      value must be greater than or equal to the index of
                      the first element in the target array, and less
                      than or equal to the index of the last element in
                      the target array minus the move count.

Description 

The syntax of the procedure is identical to the syntax of the predefined
procedure strmove.

move_r_to_l moves the elements from right to left.  In a right to left
move, the first element to be moved is the right-most (highest indexed)
element, and the last element to be moved is the left-most (lowest
indexed) element.

Even if the elements of the array to be moved are arrays themselves, the
array will be moved as a single item.

The following diagram shows the order of copying for move_r_to_l.

	       Click here to view figure.
          Figure 11-7.  Copying Order for move_r_to_l 

Fast_Fill.   

The predefined procedure fast_fill provides a generalized method of
initializing an array to a single 8 bit constant.

Usage 

     fast_fill (ptr,fill_char,count);

Parameters 

ptr                   A pointer expression.

fill_char             A constant expression.

count                 A positive integer expression that contains the
                      number of bytes to fill with fill_char.

Description 

fast_fill provides a fast alternative to for loops or assignment
statements for initializing each element of a structure or an array to
the same 8 bit value.

fill_char and ptr should of compatible types.  fill_char must also
satisfy the following requirement:

     0 <= ord(fill_char) <=255

Example 

     $standard_level 'ext_modcal'$
     program fill;
     var p100    : packed array [1..100] of char;
     var i1000   : packed array [1..1000] of integer;
     type heap_p = array [0..9] of integer;
     var p       : ^heap_p;
     begin
       fast_fill(addr(p100),' ',sizeof(p100)); {fill a string array}
                                               {with spaces.}
       fast_fill(addr(i1000),0,sizeof(i1000)); {fill an integer array}
                                               {with 0s.           }
     new(p);
     fast_fill(p,hex('ff'),sizeof(p^));        {fill an array in the }
                                               {heap to -1 (all bits on).}
     end.

Move_Fast.   

The predefined procedure move_fast provides another generalized array
copying mechanism.

Usage 

     move_fast(count,source,source_index,target,target_index) 

Parameters 

count                 A positive integer expression whose value is the
                      number of elements to move.

source                The source array from where elements will be moved.

source_index          An integer expression whose value is the index into
                      the source array of the leftmost element to be
                      moved.  The value must be greater than or equal to
                      the index of the first element in the source array,
                      and less than or equal to the index of the last
                      element in the source array minus the move count.

target                The target array to where elements will be moved.

target_index          An integer expression whose value is the index into
                      the target array to where the move begins.  The
                      value must be greater than or equal to the index of
                      the first element in the target array, and less
                      than or equal to the index of the last element in
                      the target array minus the move count.

Description 

The syntax of the procedure is also identical to the syntax of the
predefined procedure, strmove.

Move_fast provides an alternative to move_l_to_r or move_r_to_l for
generating simpler and faster code when certain restrictions are met by
the parameters.

These restrictions are:

   *   The source and target arrays must not overlap.

   *   The source and the target must have elements with the same sizes.
       The size of each element must be greater than or equal to one
       byte.

   *   If the source or the target array is packed, then the packing
       should be such that the wasted space per word; for example, space
       left between elements, should be the same for both arrays.

   *   Both the source and the target arrays must be aligned on byte
       boundaries.  Therefore, one of the following must be true:

          *   All elements of the source and the target arrays must each
              be aligned on byte boundaries.

          *   The leftmost source and target element must be aligned on
              byte boundaries, and the total size of the elements to be
              moved must be an integral multiple of one byte.

Example 

{ This example assumes certain packing which may not apply to your
implementation.  }

     TYPE
        IxType1 =  0..20;
        IxType2 = -3..17;

        Array1 = PACKED ARRAY [IxType1] of SHORTINT;
        Array2 = ARRAY [IxType2] of SHORTINT;
        Array3 = PACKED ARRAY [1..20] of -256..255;
        Array4 = CRUNCHED ARRAY [1..20] of -256..255;

     VAR
        Avar1 : Array1;
        Avar2 : Array2;
        Avar3 : Array3;
        Avar4 : Array4;
        Ix    : Integer;

     BEGIN

        Move_Fast (5, AVar2, -3, AVar1, 3);             { legal  }
        FOR Ix := 0 TO 4 DO                { equivalent FOR loop }
           AVar1[Ix+3] := AVar2[Ix-3];

        Move_Fast (5, AVar3, 2, AVar4, 9);

           { illegal, because                                    }
           { - AVar4 does not have byte-aligned elements         }
           { - AVar4[9] starts on the 27th bit of a word         }
           {      (also not byte-aligned)                        }
           { besides, the number of bits to be moved is not a    }
           { multiple of eight, anyway                           }

        Move_Fast (8, AVar4, 1, AVar4, 9)

           { legal, because                                     }
           { - even though the individual elements of AVar4 are  }
           {      not byte-aligned,                              }
           { - AVar4[1] and AVar4[9] are each byte-aligned, and  }
           { - The total size of the elements to be moved is an  }
           {   integral multiple of eight.                       }
     END;

Error Handling Routines 

Escape.   

Usage 

     escape(escape_value) 

Parameters 

escape_value          An integer expression whose value will be available
                      through the predefined function escapecode.

Description 

Calling this predefined procedure indicates that a software error has
been detected.  Execution passes to the statement following the reserved
word RECOVER of the first enclosing TRY-RECOVER statement.

The parameter is evaluated before control is passed and, its value is
available to the escapecode function.

If escape is called with no surrounding TRY-RECOVER the program aborts.

Example 

     PROCEDURE proc;
     ...
     BEGIN
        ...
        IF ( {something has gone wrong} ) THEN
           ESCAPE( 0 );
        ...
     END;
     ...
     BEGIN
       TRY
          ...
          proc;
          ...
       RECOVER
          WRITELN( 'fatal error. program terminates' );
     END.

Escapecode.   

The predefined function escapecode returns the last execution error
number.

Usage 

     escapecode

The function returns the value passed to the last implicit or explicit
call to the predefined procedure escape.

An explicit call to escape is a call that was made by the user.  In this
case escapecode returns the value of the escape code passed by the user.

An implicit call to escape is a call that was made by a subsystem on the
user's behalf or by the run-time library.  In this case, escapecode
returns a predefined value based on the type of error detected.  See the
HP Pascal/iX Programmer's Guide or the HP Pascal/HP-UX Programmer's 
Guide, depending on your implementation, for more details about the
escape code values.

If escape has never been called (implicitly or explicitly), the value
returned by escapecode is undefined.  If escapecode is called outside of
the recover part of a TRY-RECOVER statement, the value returned is
undefined.

Example 

     TRY
          ...
        { perform normal processing }

     RECOVER
        CASE escapecode OF
           ...
           { fix-up after an error that can be handled }
           OTHERWISE

              { send errors that cannot be handled }
              escape( escapecode );
        END;

The example above shows a possible control structure for trapping
software errors.  Within the recover section of the TRY-RECOVER
statement, escapecode is used to recover information about the nature of
the error that caused the trap to the recover section.  Note the use of
escapecode to pass certain errors on to a next enclosing TRY statement
with an explicit call to escape.

Parameter Mechanisms 

Haveextension.   

The predefined Boolean function haveextension determines if an extension
parameter is accessible.

Usage 

     haveextension(parameter_name) 

Parameters 

parameter_name      The name of a formal parameter in the current scope
                    or a containing scope that is EXTENSIBLE.

In a routine with extension parameters it may be necessary to check a
formal parameter to ensure that an actual parameter was supplied, as a
result of a parameter being passed by the user or being defaulted.  The
predefined function haveextension indicates, for a formal extension
parameter name, whether that parameter exists and can be accessed.

Example 

     PROCEDURE proc_with_opt_parms(     parm1 : type1;
                                    VAR parm2 : type2;
                                        parm3 : type3;
                                    VAR parm4 : type4  )
        OPTION EXTENSIBLE 2;

     BEGIN
        ...
        IF (haveextension( parm4 )) THEN

           { implies that parm4 and parm3 have values }
           ...

        IF (haveextension( parm3 )) THEN

           { implies that parm3 has values }
           ...

        ...
     END;

     proc_with_opt_parms( var1, var2 );
     ...
     proc_with_opt_parms( var1, var2, var3 );

In the previous example, haveextension is used to determine whether
either or both of the EXTENSIBLE parameters are passed in the call to the
procedure.  Note that if parm4 is present, then by definition parm3 must
also be present.  See the description of routine OPTION EXTENSIBLE for
more information.

In the first call to proc_with_opt_parms, both calls to haveextension
return false because none of the extension parameters are passed.  In the
second call, haveextension returns true for the third parameter only.

     PROCEDURE proc_with_opt_parms(     parm1 : type1;
                                    VAR parm2 : type2;
                                        parm3 : type3;
                                    VAR parm4 : type4  )
             OPTION EXTENSIBLE 2
                    DEFAULT_PARMS ( parm3 := 0,
                                    parm4 := nil  );

     BEGIN
        ...
        IF (haveextension( parm3 )) THEN
           ...
        IF (haveextension( parm4 )) THEN
           ...
        ...
     END;

In the above example, haveextension( parm4 ) returns true only if the
fourth parameter was actually supplied by the user.  If it was not
supplied, then the default value is ignored, and the parameter is not 
passed.

Haveextension( parm3 ) is true if either of the following conditions are
true:

   *   The third or fourth parameters are supplied by the user.

   *   The fourth parameter is supplied and the third is defaulted.
       Because the fourth parameter is EXTENSIBLE, and, therefore, by
       definition all parameters to its left must be passed, the default
       value for the third parameter is passed even though it was not
       supplied by the user.

Haveoptvarparm.   

The predefined Boolean function haveoptvarparm determines if a default
reference parameter is accessible.

Usage 

     haveoptvarparm(parameter_name) 

Parameters 

parameter_name      The name of a default formal parameter of this or a
                    containing scope.

In a routine with default reference parameters, it may be necessary to
check a formal parameter to ensure that its actual parameter was supplied
by the user.  The predefined function haveoptvarparm indicates for a
formal reference parameter name whether the corresponding actual
parameter was supplied by the user.

The argument to haveoptvarparm must be the name of a formal parameter
that:

   *   Is a VAR, ANYVAR, or PROCEDURE/FUNCTION parameter.

   *   Specifies a default value of NIL. See the routine OPTION
       DEFAULT_PARMS.

Example 

     PROCEDURE proc_with_opt_parms( VAR parm1 : type1;
                                    VAR parm2 : type2;
                                    VAR parm3 : type3  )
              OPTION DEFAULT_PARMS( parm2 := nil,
                                    parm3 := nil  );

     BEGIN
        ...
        IF (haveoptvarparm( parm2 )) THEN        { ok to use parm2 }
           ...

        IF (haveoptvarparm( parm3 )) THEN        { ok to use parm3 }
           ...
     END;

The procedure proc_with_opt_parms in the previous example has three VAR
parameters, two of which are optional.  Before using one of the two
parameters within proc_with_opt_parms, a check is made to ensure that the
parameters were supplied by the user.  This check is accomplished by
calling haveoptvarparm with the name of the parameter in question as its
argument.

Routine Mechanisms 

Call.   

The predefined procedure call invokes a procedure.

Usage 

     call(procedure_expression) 
     call(procedure_expression,parameter ...) 

Parameters 

procedure_expression   An expression whose value is a reference to a
                       procedure whose formal parameter list is congruent
                       with the parameters specified in the call.

parameter              An actual parameter that is compatible with the
                       corresponding formal parameter of the PROCEDURE
                       type of procedure_expression, that is passed to
                       the invoked procedure.

Description 

The predefined procedure call causes the indicated procedure to be called
with the indicated parameters.

If, during the execution of the procedure, call accesses any non-local
variables, the variables accessed are the variables that were accessible
at the time the reference to the procedure was made, when it was passed
as an argument to the predefined function, addr.  It is an error if the
procedure expression has the value NIL or is undefined.  It may not be
possible to detect an undefined procedure reference.

Example 

     TYPE
        procedure_type = PROCEDURE( i : integer );

     VAR
        int : integer;
        proc_var : procedure_type;

     PROCEDURE proc( int : integer );
     BEGIN
        ...
     END;

     BEGIN
        proc( int );

        proc_var := addr( proc );
        call( proc_var, int );
     END;

In the above example, the two calls to the routine proc are effectively
identical.

Fcall.   

The predefined function fcall invokes a function.

Usage 

     fcall(function_expression) 
     fcall( function_expression, parameter ... ) 

Parameters 

function_expression    An expression whose value is a reference to a
                       function whose formal parameter list is congruent
                       with the parameters specified in the call.

parameter              An actual parameter that is compatible with the
                       corresponding formal parameter of the FUNCTION
                       type of function_expression, that is passed to the
                       invoked function.

The predefined function fcall causes the function referenced by the first
FUNCTION variable parameter to be invoked with the supplied parameters.

The type returned by fcall is the same as the type returned by the
FUNCTION expression.

See the description of call for more information.

Size Functions 

Bitsizeof.   

The predefined function bitsizeof returns an integer representing the
size of its argument in bits.

Usage 

     bitsizeof(variable) 
     bitsizeof(record_variable,tag_value ...) 
     bitsizeof(type_name) 
     bitsizeof(record_type_name,tag_value ...) 
     bitsizeof(struc_constant) 
     bitsizeof(string_literal) 

Parameters 

variable            The name of a variable.

record_variable     The name of a record variable with variants.

tag_value           The name of a case constant in the variant part of a
                    record declaration.  Case constants for nested
                    variants may appear separated by commas.

type_name           The name of a type.

record_type_name    The name of a record type with variants.

struc_constant      The name of an array, record, set, or string
                    constructor.

string_literal      A string literal.

The bitsizeof function returns the number of bits needed to represent the
data value part of a data item of the given type, or the actual allocated
size of a variable.  If the first parameter is a record type or variable
with variants, a variant may be selected by specifying a case constant
with the subsequent parameters.  Otherwise, the size with the largest
variant is used.

bitsizeof(type) returns the minimum number of bits of storage for the
type, and bitsizeof(variable) returns the number of bits of storage for
the variable.

For an ANYVAR parameter, two cases exist:  If an additional hidden size
parameter is passed along with the ANYVAR parameter, bitsizeof gives the
number of bits in the number of bytes allocated to represent the actual
parameter.  If the hidden length parameter is not passed, bitsizeof gives
the number of bits required to represent the formal parameter as a given
type.

Example 

     TYPE
        int_type = integer;
        rec_type = RECORD
           int : integer;
           CASE flag: Boolean OF
             true: ( r  : real );
             false:( lr : longreal );
             end;
     VAR
        int  : int_type;
        rec  : rec_type;
        size : integer;

     BEGIN
        ...
        size := bitsizeof( int );
        size := bitsizeof( int_type );

        size := bitsizeof( rec, true );
        ...
     END;


NOTE bitsizeof is allowed in CONST declarations except for ANYVAR, VAR string, and conformant array parameters.
Sizeof. The predefined function sizeof returns an integer representing the size of its argument in bytes. Usage sizeof(variable) sizeof(record_variable,tag_value ...) sizeof(type_name) sizeof(record_type_name,tag_value ...) sizeof(struct_constant) sizeof(string_literal) Parameters variable The name of a variable. record_variable The name of a record variable with variants. tag_value The name of a case constant in the variant part of a record declaration. Case constants for nested variants may appear separated by commas. type_name The name of a type. record_type_name The name of a record type with variants. struct_constant The name of an array, record, set, or string constructor. string_literal A string literal. The predefined function sizeof returns the number of bytes of storage required to represent the data value part of a data item of the given type, or the actual allocated size of a variable. If the first parameter is a record type or variable with variants, a variant may be selected by specifying a case constant with the subsequent parameters. sizeof(type) returns the minimum number of bytes for the type. sizeof(variable) returns the number of bytes of storage for the variable. Otherwise, the size of the largest variant is returned. For a variable of a simple data type, the number returned by sizeof is equivalent to the storage required for the variable in the unpacked context. For example, if the variable is type char or Boolean, sizeof returns 1. For an ANYVAR parameter, two cases exist: If an additional hidden size parameter is passed along with the ANYVAR parameter, sizeof gives the actual number of bytes allocated to represent the actual parameter. If the hidden length parameter is not passed, sizeof gives the number of bytes required to represent the formal parameter. For conformant array parameters, the function sizeof is the actual size of the parameter. Example TYPE byte = 0..255; big_record = RECORD CASE Boolean OF true: ( arr : array [ 1..200 ] of byte ): false: ( f1 : integer; ... f99 : char ); BEGIN ... IF (sizeof(big_record,true) <> sizeof(big_record,false)) THEN BEGIN writeln ( 'variant size mismatch by', abs(sizeof(big_record,true)-sizeof(big_record,false)):1, 'bytes' ); HALT (1); END; ... END.
NOTE sizeof is allowed in CONST sections except for ANYVAR, VAR s, and conformant array parameters.


MPE/iX 5.0 Documentation