The Pascal Library

download The Pascal Library

of 19

Transcript of The Pascal Library

  • 7/27/2019 The Pascal Library

    1/19

    10/7/13 The Pascal Library

    www.templetons.com/brad/alice/language/language8.html

    The Pascal Library

    In the last chapter, we described the standard library subprograms related to I/O. In this chapter, we will deal

    with other commonly used subprograms. Note that the HELP facility can also give information on most of these

    subprograms.

    Conversion Functions

    The following functions convert one type of data to another.

    round(x)

    This converts a real expression x into an integer value by rounding it up or down to the nearest integer.

    Therefore, round(3.2) has the value 3 while round(3.7) has the value 4. round(-3.2) has the value -3

    while round(-3.7) has the value -4.

    trunc(x)

    This converts a real expression x into an integer value by truncating the fractional part. Therefore the

    expressions trunc(3.2) and trunc(3.7) both have the value 3. trunc(-3.2) and trunc(-3.7) both have

    the value -3.

    chr(i)

    This converts an integer expression i into a char value. The integer is converted to whatever character has

    the same ASCII representation. This means that the integer must lie inside the values for the ASCII character setin this case 0 to 255.

    ord(c)

    This converts a scalar type expression into an integer. char values are translated into the integer that has the

    same ASCII representation. This means that for any char value c,

    chr( ord(c) ) equals c

    The effect oford on enumerated types was described in Chapter 3.

    The ord function is a non-standard function because its arguments can have any scalar type. For this reason, it

    cannot be passed as an function argument to another subprogram.

    Frac(x)

    This returns a real number whose value is the fractional part of the real value x. For example,

    n := Frac(7.3);

  • 7/27/2019 The Pascal Library

    2/19

  • 7/27/2019 The Pascal Library

    3/19

    10/7/13 The Pascal Library

    www.templetons.com/brad/alice/language/language8.html 3

    sqr(x)

    returns the square ofx. x may be real orinteger, and the result will have the same type as the argument.

    sqrt(x)

    returns the square root ofx. x may be real orinteger. The result is always real.

    sin(x)

    returns the sine ofx. x may be real orinteger, and gives an angle in radians. The result is always real.

    cos(x)

    returns the cosine ofx. x may be real orinteger, and gives an angle in radians. The result is always real.

    arctan(x)

    returns the arctangent ofx. x may be real orinteger. The result is always real, and gives an angle in radians

    ln(x)

    returns the natural logarithm ofx (base e). x may be real orinteger. The result is always real.

    exp(x)

    returns the numbere to the powerx. x may be real orinteger. The result is always real.

    The functions abs and sqr are non-standard, in that they may return either an integer or real number. For this

    reason, they may not be passed as function arguments to subprograms.

    Order Functions

    Order functions can be applied to any scalar type. The ``successor'' function succ has the form

    next := succ(value);

    where value is any scalar value. The result returned by succ is the next value in the scalar type. For example, ifvalue is an integer, succ returns the next integer, so

    succ(3) = 4

    Ifvalue is an enumerated type, succ returns the next value in the enumerated list. Thus if you define

    type

    days = (sun,mon,tue,wed,thu,fri,sat);

    you would have

  • 7/27/2019 The Pascal Library

    4/19

    10/7/13 The Pascal Library

    www.templetons.com/brad/alice/language/language8.html 4

    succ(sun) = mon

    succ(mon) = tue

    { And so on }

    If you try

    succ(sat)

    you will be given an error message. sat is the last element in the enumerated type and has no successor.

    The ``predecessor'' function pred is the converse ofsucc. It has the form

    previous := pred(value);

    pred returns whatever comes before the given value. For example,

    succ(3) = 2

    succ(tue) = mon

    Ifvalue has no predecessor, Alice will give you an error.

    Packing Functions

    Other implementations of Pascal have functions named pack and unpack. pack takes the values that are stored

    in a normal array and assigns them one by one to a packed array. unpack takes the values that are stored in a

    packed array and assigns them one by one to a normal array.

    Alice recognizes the names pack and unpack, but the subprograms just give an error if called.

    Dynamic Memory Allocation

    The new procedure can be used to allocate memory dynamically at execution time. The memory is allocated

    from a store of memory called the heap. The simplest form ofnew is

    new(p);

    where p is a pointer variable. The procedure will allocate sufficient memory space to contain the sort of data that

    p points to. For example, ifp is declared

    varp : ^integer;

    new will obtain enough space to hold an integer. Ifp is a pointer to some record type, new will allocate enough

    space to hold a record of that type. When the space has been obtained, new will set up p to point at the space

    that has been obtained.

    As a simple example, the following code uses new to set up a linked list of records.

  • 7/27/2019 The Pascal Library

    5/19

    10/7/13 The Pascal Library

    www.templetons.com/brad/alice/language/language8.html 5

    type

    listptr = ^listelement;

    listelement = record

    link : listptr;

    other : {Various things};

    end;

    var

    root, pl : listptr;

    begin

    {Get root of list}new(root);

    pl := root;

    for i := 1 to 10 do begin

    new(pl^.link);

    pl := pl^.link;

    end;

    pl^.link := nil;

    {And so on}

    This allocates 10 new list elements and links them together in a linked list.

    Note that new is one of the few ways to initialize a pointer. All the other ways involve calls to Pointer functions(described later in this chapter).

    A second form ofnew is used when allocating space for records with variant fields. This has the form

    new(p,t1,t2,...);

    where p is a pointer to the record type, and t1,t2,... are values for one or more tag fields of the variant part.

    By plugging these values into the various tag-fields, new can determine the correct amount of memory to allocate

    Note that new does not put these values into the tag-fields of the record it creates; it simply uses these values to

    determine how big the record should be. Ifnew is not supplied with enough tag-fields to totally determine the sizeof memory required, it will allocate enough memory to hold the largest possible record of this type. Alice ignores

    the tag fields and always does this.

    The dispose procedure is used to release memory that has been allocated through new. dispose should be

    called with the same arguments that were passed to the new procedure that allocated the memory. Therefore you

    should use

    dispose(p);

    dispose(p,t1,t2,...);

    This is the only way that memory allocated by new may be freed up. In particular, memory allocated inside a

    subprogram is notautomatically released when the subprogram terminates. You must release the memory

    explicitly with dispose. Releasing the memory makes it available for re-allocation in later calls to new, but it

    does not decrease the size of your program.

    If you call dispose and give a file variable as an argument, Alice will close the file associated with the variable.

    The Mark procedure is used to find out the current value of the heap pointer. The usage is

    Mark(variable);

  • 7/27/2019 The Pascal Library

    6/19

    10/7/13 The Pascal Library

    www.templetons.com/brad/alice/language/language8.html 6

    where the variable is a pointer.

    The Release procedure sets the heap pointer back to a particular value. Its usage is

    Release(variable);

    where the variable is a pointer.

    Both Mark and Release are found in TURBOLIB.AP. They are intended for Turbo Pascal compatibility, andshould not be used in new programs; instead, Dispose should be used. Also note that Mark and Release are

    not compatible with the New/Dispose form of memory allocation.

    To find out how large a block can be allocated, use the MaxAvail function. It returns the size of the largest

    block of contiguous free storage available on the heap.

    To find out the total amount of free memory, use the MemAvail function. It returns the total amount of storage

    available on the heap.

    Both MaxAvail and MemAvail return an integer specifying the number of 16-byte units called `paragraphs.''The returned value is an integer; if it is less than zero, the actual value can be computed as a real number using

    the expression MaxAvail + 65536.0, or MemAvail + 65536.0. In the current release ofAlice, the values will

    always be greater than zero.

    The GetMem and FreeMem routines are used to allocate and deallocate dynamic memory blocks of a user-

    specified size.

    GetMem(variable, n);

    will allocate n bytes from the heap and set the pointervariable to point to that block. This is more general than

    new, since it is not limited to allocating just enough space for a particular instance of a variable.

    The MaxAvail function can be used to find out in advance if the call to GetMem will succeed or fail.

    FreeMem(variable, n);

    will return the memory pointed to by variable to the free pool for subsequent re-allocation. The pointer should

    be one set by GetMem, and the value ofn should match the value in the call to GetMem. It is important that you

    not call FreeMem on any pointer not allocated by GetMem, and that you not accidentally free the same memory

    twice. You should also be careful not to keep copies of the pointer from GetMem in other pointer variables, and

    then try and refer through them after the memory has been deallocated by FreeMem.

    String Manipulation Routines

    String manipulation routines manipulate string constants and variables with string types. Our descriptions of these

    routines will give examples of source code using each routine, followed by output from this source code.

    The first set of functions in this section are taken from Watcom Pascal.

    StrConcat(str1,str2);

  • 7/27/2019 The Pascal Library

    7/19

    10/7/13 The Pascal Library

    www.templetons.com/brad/alice/language/language8.html 7

    This procedure concatenates the contents ofstr2 on the end ofstr1.

    str1 := 'hello';

    str2 := ' there';

    StrConcat(str1,str2);

    writeln(str1);

    - - - - -

    hello there

    Note the string concatenation can also be performed with the ``+'' operator.

    StrDelete(string,N,position);

    This procedure deletes N characters from string. Position is an integer giving the subscript of the first

    character to be deleted.

    str := 'The quick brown fox';

    StrDelete(str,2,5);

    writeln(str);

    - - - - -The ick brown fox

    This routine is similar to the Turbo Pascal Delete routine.

    StrInsert(str1,str2,N);

    This procedure inserts the contents ofstr2 into str1. The first character ofstr2 will become character N of

    str1.

    str := 'The quick fox';

    StrInsert(str1,'brown',5);writeln(str);

    - - - - -

    The brownquick fox

    This routine is similar to the Turbo Pascal Insert routine.

    i := StrLen(string);

    This function returns an integer giving the length of a string. For a string constant, this is the number of characters

    in the constant. For a string variable, it is the number of characters currently stored in the variable. If the variable

    is not full, it will be the number of characters up to but not including the StrEnd that follows the last character in

    the string.

    str := 'abcdef';

    writeln(StrLen(str));

    str := 'abc';

    writeln(StrLen(str));

    writeln(StrLen('xyz');

    - - - - -

    6

    3

  • 7/27/2019 The Pascal Library

    8/19

    10/7/13 The Pascal Library

    www.templetons.com/brad/alice/language/language8.html 8

    3

    This routine is similar to the Turbo Pascal Length routine.

    i := StrScan(str1,str2);

    This function looks for the string str2 inside str1. If it is found, StrScan returns the subscript where str2

    begins in str1. If the string is not found, StrScan returns 0.

    i := StrScan('hello there','the');

    writeln(i);

    - - - - -

    7

    This routine is similar to the Turbo Pascal Pos routine.

    i := StrSize(string);

    This function returns an integer giving the maximum length of a string. If the string is a string constant, this is the

    number of characters in the string. If the string is a string variable, this is the maximum number of characters that

    the string can hold, regardless of how many it holds at the moment.

    var

    str :packed array [1..10] of char;

    ...

    writeln(StrSize('abc'));

    str := 'abc';

    writeln(StrSize(str));

    - - - - -

    3

    10

    SubStr(str1,N,position,str2);

    This procedure obtains a copy of part ofstr1. N is the length of the substring and position is the subscript

    where the substring starts. The substring that is obtained is copied into str2.

    str1 := 'Hello there';

    SubStr(str1,2,3,str2);

    writeln(str2);

    - - - - -

    ll

    Also of note for this purpose is the Turbo Pascal Copy function.

    The remaining functions in this section are taken from Turbo Pascal.

    Delete(str, pos, num);

    This procedure deletes a substring of length num starting at position pos in the string variable str. The remaining

    characters (if any) in the string are shifted left. This routine is similar to the Watcom StrDelete routine.

  • 7/27/2019 The Pascal Library

    9/19

    10/7/13 The Pascal Library

    www.templetons.com/brad/alice/language/language8.html 9

    Insert(src, dest, pos);

    This procedure inserts the string src into the string dest at position pos. The variables src and dest are both

    of type string; pos is of type integer. An error message will be issued if the pos is past the end of the string, or

    the string becomes too long. This is stricter error checking than that provided by the same routine in the Turbo

    Pascal compiler. This routine is similar to the Watcom StrInsert routine.

    Copy(str, pos, num);

    This function returns a substring of the string variable str of length num starting at position pos. It returns the null

    string (i.e. a string of length zero) if pos is greater than the length of the string.

    Length(str)

    This function returns the length of the string argument in characters. For a string constant, this is the number of

    characters in the constant. For a string variable, it is the number of characters currently stored in the variable.

    Length gets its value from the special length byte kept at the zeroth index of every string. It is similar to the

    Watcom Strlen function.

    Pos(srch, str);

    This function returns the position in the string str at which the string srch is found. It returns 0 ifsrch was not

    found in str. For example,

    i := Pos('exec', 'autoexec.bat');

    will cause i to have the value 5, while

    i := Pos('gremlin', 'halloween');

    will cause i to have the value 0. This is similar to StrScan

    Str(val, str)

    This procedure puts the value of the given variable val (which may be integer or real) into the given string

    variable str as an ASCII representation of the number. The variable val can actually have format specifiers of

    the same type found in write procedure calls. One can specify a field width for integers and reals. Reals may

    also have a precision field, just as with write. In general

    Str(i:n, dest);

    writeln(dest);

    is the same as:

    writeln(i : n);

    ifdest is a string large enough to hold the written number.

    Note that Alice places a space in front of integer operands if no field width is provided. A field width of zero

  • 7/27/2019 The Pascal Library

    10/19

    10/7/13 The Pascal Library

    www.templetons.com/brad/alice/language/language8.html 10

    eliminates this. This space is not output when Borland deviations (+b) are enabled.

    An error occurs if the string is not large enough to hold the number.

    Val(str, variable, code);

    This procedure is the inverse of the str procedure; it examines the string contained in str and converts it to a

    number which it stores in var. The type of the number is either real or integer, depending on the type ofvar.

    Leading and trailing spaces are not permitted; the valid formats for the number are the same as those for

    constants in Alice Pascal. In addition, real numbers with nothing before the decimal point (e.g. ".1") are

    acceptable.

    If the conversion is successful, the integer variable code is set to zero; otherwise, it contains an index into str of

    the character on which the conversion failed. If this is the case, the value ofvar is undefined.

    For example,

    Val('7.8', n, stat);

    will set n to 7.8 and stat to zero, while

    Val('7y2', n, stat);

    will result in stat being 2 (the index of the letter y in the string) and the value ofn will be undefined.

    UpCase(c);

    This function returns a character which is the upper-case equivalent of the characterc. For example,

    ch := UpCase('b');

    will result in ch having the value 'B'. This routine is handy if you want to accept user input in either upper or lower

    case.

    Pointer Functions

    There are a variety of routines that deal with addresses and pointers. Most of these use values of the Pointer

    type, the special Alice built in type that is assignment compatible with all other pointers.

    i := address(variable);

    This function obtains the actual memory address of its argument. The argument must be a variable name, a

    subscripted variable, a field inside a record variable, or an indirectly-referenced variable. address returns an

    integer that gives the machine address that has been allocated to that variable. If a machine address does not fit in

    an integer, as is the case with the 8086 processor in the IBM-PC, the result returned is actually only part of the

    address, namely the offset. For example,

    i := address(v);

  • 7/27/2019 The Pascal Library

    11/19

    10/7/13 The Pascal Library

    www.templetons.com/brad/alice/language/language8.html 1

    obtains the integer offset of the variable v.

    You can also specify a second argument foraddress, indicating whether you want the segment containing the

    variable or the offset of the variable within the segment. If the argument is the integer0, you get the offset; if it is

    any other integer, you get the segment. If this second argument is omitted, address returns the offset. For

    example,

    i := address(v,1);

    obtains the segment that contains the variable v.

    address is unique to Alice.

    i := Ofs(variable);

    This function is similar to address, except that it does not take a second argument and always returns the offset.

    [Found in TURBOLIB.AP]

    p := MakePointer(variable);

    This function is much like address except that it returns a Pointer type value instead of an integer. This can be

    assigned to any valid Pascal pointer type. MakePointer is unique to Alice. Unlike address, MakePointer

    does not need to deal with offsets and segments, as a variable ofPointer type always holds a pointer. Note,

    however, that in SMALL model Alice, such pointers may only point within Alice's 64K data segment.

    p := Addr(variable);

    This is Turbo Pascal's version ofMakepointer. It returns a pointer to the given variable. For example,

    var

    i : ^integer;

    ...

    i := Addr(v);

    i^ := 10

    Places 10 (indirectly) into v, assuming it is an integer variable.

    [Found in TURBOLIB.AP]

    p := RawPointer(offset,segment);

    This function converts an integer address into a Pointer type. As such, it is the inverse ofaddress. The offset

    argument is an integer giving an offset within a segment, and the optional segment argument is an integer giving a

    segment number. If not provided, the second argument is assumed to be the Data Segment. In small-model

    Alice, this segment number must either be omitted or equal to the Data Segment (Dseg). The value returned by

    RawPointer has the Pointer type. RawPointer is unique to Alice.

    p := Ptr(segment, offset);

  • 7/27/2019 The Pascal Library

    12/19

    10/7/13 The Pascal Library

    www.templetons.com/brad/alice/language/language8.html 12

    This function creates a pointer from two integers, and is the Turbo Pascal equivalent ofRawPointer. None of

    the parameters are optional, and in SMALL model Alice, the first parameter must be equal to the Data Segment

    as returned by DSeg.

    i := peek(address);

    This function returns the value that is at the given memory address. The address argument is given as an integer

    The value that is returned is a single byte and will therefore be in the range 0..255. On the IBM PC, only the first64K of physical memory may be accessed this way. This 64K is not the Data Segment ofAlice. To access

    other addresses, use Mem_To_Var (described below).

    poke(address,value);

    This procedure stores a value in the given address. The address is given as an integer. Since poke only stores a

    single byte, the value argument should be in the range 0..255. If it is not, poke will use value mod 256. On

    the IBM PC, only the first 64K of physical memory may be accessed this way. This is not the Data Segment

    used by Alice. To access other addresses, use Var_To_Mem (described below).

    Var_To_Mem(variable,offset,segment)

    This routine copies a variable to an absolute address in memory. On an IBM-PC, this address is specified with

    two integers, an offset and a segment. Great care should be taken when using this routine, as writing improperly

    on absolute memory can easily crash your machine. The segment argument is optional, and defaults to the Data

    Segment. Be warned when writing into the Data Segment that this routine does not mark the memory it touches

    as initialized.

    Mem_To_Var

    This routine copies from absolute memory into the specified variable. It is the inverse ofVar_To_Mem. On an

    IBM-PC, the address is specified with two integers providing the offset and segment of the desired memory

    location. The number of bytes copied equals the size of the variable in question.

    Move(src, dest, count)

    This procedure copies a number of bytes specified by the integercount from the location of the variable

    specified by src to the location of the variable specified by dest. Both src and dest may be of any type. It is

    up to you to make sure there is enough room in dest to contain the data. See also Var To Mem and Mem ToVar. This routine is contained in TURBOLIB.AP.

    FillChar(variable, num, value)

    This procedure fills memory with the given charactervalue, starting at the base address of the specified

    variable, for a length ofnum characters. The var can be of any type; num must be an integer, and the value

    must be a character orbyte.

    This routine is very fast (much faster than doing it yourself in a loop). It is up to you to make sure that there is

  • 7/27/2019 The Pascal Library

    13/19

    10/7/13 The Pascal Library

    www.templetons.com/brad/alice/language/language8.html 13

    enough room in the variable to contain the data.

    Note that strings have a length byte in the zeroth position; this byte will get overwritten if you pass a string to

    FillChar.

    This routine is contained in TURBOLIB.AP.

    i := Dseg;

    This function returns the value of the Data Segment as an integer. In small model Alice, this is the segment in

    which all variables are found. When constructing pointers (for example, using ptr), you should use the value of

    dseg. This routine is contained in TURBOLIB.AP.

    i := Cseg;

    This function returns the value of the Code Segment as an integer. This value should almost never be used for

    anything, since Alice is an interpreter. (For more information about the differences between interpreters and

    compilers, refer to the section on converting between Turbo and Alice). The Cseg function returns the value ofone of the code segments of the Alice interpreter. Any offsets into the Cseg that the program uses will be

    meaningless; also, using Cseg in the setting of interrupt vectors is incorrect. This routine is contained in

    TURBOLIB.AP.

    i := Sseg;

    This function returns the value of the Stack Segment as an integer. In small model Alice, this is the same as the

    Data Segment. This routine is contained in TURBOLIB.AP.

    i := Seg(variable);

    This function returns the segment address of the given variable. In small model Alice, this will always be the same

    as the program's data segment (i.e., dseg). This routine is found in TURBOLIB.AP.

    Random Number Generation

    Alice includes a function called random that generates pseudo-random numbers. Unfortunately, maintaining

    compatiblity with both Watcom and Turbo Pascals is impossible with this function, so two versions exist. When

    Turbo Pascal features are disabled with the ``-t'' option, random acts as it does in Alice 1.2 and WatcomPascal. Otherwise it acts as the random function of Turbo Pascal.

    For both systems,

    initrandom(seed,upper);

    initializes a pseudo-random number generator. Both seed and upper are integers. Different values ofseed will

    give different number sequences; identical values ofseed will give identical sequences. When using Alice

    1.2/Watcom random numbers, these will be generated in the range 0..(upper-1).

  • 7/27/2019 The Pascal Library

    14/19

    10/7/13 The Pascal Library

    www.templetons.com/brad/alice/language/language8.html 14

    The actual random numbers are obtained from a function named random. If you disable Turbo Pascal

    compatibility by invoking ALICE with the -t option, the call to random has the form

    i := random;

    This returns a pseudo-random integer. You may not call random until you have initialized the random number

    generator with initrandom.

    If you do not disable Turbo Pascal features, the call to random has the form

    i := random(N);

    where N is an integer. This generates a pseudo-random integer in the range 0..N-1. In this case, you do not

    have to call initrandom first. If you omit the N as in

    a := random;

    the function will return a pseudo-random real number that is strictly less than 1.0 and greater than or equal to

    0.0.

    Randomize;

    This procedure re-seeds the random number generator from the system clock, so that a different sequence of

    values will be produced for every run. [Found in TURBOLIB.AP]

    System Calls

    The following routines let you perform system calls. Users should normally never need to use these.

    i := SysFunc(p,arg,arg,arg,...);

    This function calls a system function. The p argument is a Pointer type pointing to the memory location of the

    function to be called. The function is passed (in Microsoft C calling style) an itneger argument count and pointers

    to the top and bottom of a vector of arguments. The value returned by SysFunc is the value returned by the

    system function. SysFunc comes from Watcom Pascal, but is not compatible with it on the IBM-PC.

    SysProc(p,arg,arg,arg,...);

    This procedure works the same way as SysFunc. It is used to call system routines that do not return a value.SysProc comes from Watcom Pascal, but is not compatible with it on the IBM-PC.

    Internal C Routines

    The following routines all make calls to a special internal library of useful routines contained in Alice. These

    routines are not intended for general users, and no guarantees are made they they will remain the same from one

    Alice release to the next. The Alice distribution disks come with Pascal library routines that make use of these

    internal features. To be safe, make use of the libraries instead of calling these ``CProcs'' directly. These routines

    are all unique to Alice.

  • 7/27/2019 The Pascal Library

    15/19

    10/7/13 The Pascal Library

    www.templetons.com/brad/alice/language/language8.html 15

    i := CIntFunc(args);

    calls a C function that returns an integer. For more information, see the Alice User Guide.

    l := CLongFunc(args);

    calls a C function that returns a long integer. CLongFunc actually returns a pointer to this long integer. The long

    integer is expressed as a record with two integer fields named low and high. These contain the two halves of

    the long integer. For more information, see the Alice User Guide.

    p := CPtrFunc(args);

    calls a C function that returns a pointer. For more information, see the Alice User Guide.

    CProc(args);

    calls a C function that does not returns a value. For more information, see the Alice User Guide.

    p := SysPointer(i);

    returns the value of an Alice control variable. For more information, see the Alice User Guide. SysPointer is

    unique to Alice.

    Outside World Interface

    Chain(filename);

    runs the Alice program contained in the specified file. There is a similar routine in Turbo Pascal; however, it is

    not the same. Turbo's Chain routine only runs special Turbo chain files, and preserves variables from one

    program to the other. In Alice, the chain routine will erase the current program, and load and run the new one.

    This is found in the Useful DOS routines library.

    Execute(filename);

    This routine executes a DOS program in the same way that the AliceDOS command does. The command is

    executed, and control is returned to the running Alice program when it terminates. The ``COMMAND.COM''

    shell program is not used, so commands built into it like ``DIR'' and ``COPY'' may not be used directly. Notethat sufficient memory must be available to execute the command at the same time as Alice. This is found in the

    Useful DOS routines library.

    File and Directory Handling Routines

    ChDir(path);

    This routine changes the DOS current directory to the specified path. If the string includes a leading drive

    specifier, the current drive is changed as well. For example,

  • 7/27/2019 The Pascal Library

    16/19

    10/7/13 The Pascal Library

    www.templetons.com/brad/alice/language/language8.html 16

    ChDir('c:\data');

    will set the current drive to be C:, and the current directory to be the \data directory on that drive.

    If you change directories, any relative pathnames (i.e. pathnames that are not completely specified from the root

    directory down) will no longer be valid. In particular, this applies to the save file name. This routine is contained

    in TURBOLIB.AP.

    Erase(filename);

    This procedure erases the specified file from the disk. It is important that you do not erase a file that is currently

    active (that is, opened using reset orrewrite orappend). This routine is contained in TURBOLIB.AP.

    GetDir(drive, stringvar);

    This procedure stores into the specified string variable the current directory for the specified drive. The drive is

    an integer, 1 for A:, 2 for B: and so on. If drive is 0, the current drive is assumed. For example,

    GetDir(3, currdir);

    will store into the string variable currdir the current directory for drive C:. A typical directory string would be

    '\data\first'. If the current directory for the specified drive is the root directory, the string variable will contain the

    null string (i.e. StrLen(currdir) will be zero).

    This routine is contained in TURBOLIB.AP.

    MkDir(path);

    This procedure creates a new directory on the disk, whose name is contained in the string argument path. Thisnew directory is always created on the current drive. For more information on directories, see the DOS manual.

    RmDir(path);

    This procedure removes (i.e., erases) a directory from the disk. You cannot remove a directory that contains

    files or other directories. Refer to the DOS manuals for more information about directory handling. This routine is

    contained in TURBOLIB.AP.

    Rename(oldpath, newname);

    This routine changes the name of a file or directory on disk. oldpath specifies the name (and optional path) of

    the file or directory to be renamed, and newname contains the new name. This routine is contained in

    TURBOLIB.AP.

    Miscellaneous Routines

    pause;

  • 7/27/2019 The Pascal Library

    17/19

    10/7/13 The Pascal Library

    www.templetons.com/brad/alice/language/language8.html 17

    When Alice has ``Debug On'' and it encounters a call to the pause procedure, the effect is the same as if a

    breakpoint was triggered while running the program. The program will stop and wait for run-time commands

    (e.g. going into immediate mode). When Alice has ``Debug Off'', the pause procedure has no effect. If you give

    pause an argument (as in pause(1)), the program will pause regardless of whether Debug is On or Off. pause

    comes from Watcom Pascal.

    i := SizeOf(variable);

    This function returns the number of bytes of storage that are allocated to a particular variable. With string

    variables, SizeOf is equivalent to StrSize + 2. SizeOf is found both in Alice and Turbo Pascal, but the

    Alice version does not allow a type as an argument (i.e. SizeOf(integer) is invalid).

    Delay(n)

    This procedure simply delays forn milliseconds, where n is an integer. The system clock "ticks" every 55

    milliseconds, and this limits the accuracy ofdelay. Note that the system clocks on all members of the PC family

    run at the same speed, so a call to delay will produce a consistent delay regardless of whether it's running on a

    PC, an XT or an AT.

    You can use the break key to stop the delay and interrupt the execution of your program.

    Halt(n);

    The halt routine will terminate your program and return to Alice. The argument is optional; in the Turbo Pascal

    version of this routine, the argument is the "return value" or "error level" or "exit status" of the program that is

    passed back to DOS.

    Intr(intnum, regrec);

    This procedure generates a software interrupt of type intnum (an integer) and transfers register values into and

    out of the interrupt routine using the record regrec. The variable regrec should be declared as follows:

    type regs = record

    AX,BX,CX,DX,BP,SI,DI,DS,ES,Flags : Integer;

    end;

    var

    regrec : regs;

    The various register fields should be set to whatever values the registers ought to contain at the time the softwareinterrupt is issued; when the Intr procedure returns, the various fields of the record will hold the register

    contents as of the completion of the interrupt.

    The Flags field may be read from, but its value is not used to change the actual hardware flags register.

    It is important that the full record be used, not a shorter version of it, since the routine that copies the hardware

    registers into the regrec record assume the full record is available.

    Use ofIntr should be avoided, since there are higher-level functions for almost everything.

  • 7/27/2019 The Pascal Library

    18/19

    10/7/13 The Pascal Library

    www.templetons.com/brad/alice/language/language8.html 18

    MsDos(regrec);

    This procedure executes the software interrupt that interfaces to the MSDOS operating system. It is equivalent

    to Intr($21, regrec). It transfers register values into and out of the MSDOS call using the record regrec.

    The variable regrec should be declared as follows:

    type regs = record

    AX,BX,CX,DX,BP,SI,DI,DS,ES,Flags : Integer;

    end;var regrec : regs;

    The various register fields should be set to whatever values the registers ought to contain at the time that

    MSDOS is called; when the MsDos procedure returns, the various fields of the record will hold the register

    contents as of the completion of the call to MSDOS.

    The Flags field may be read, but its value is not used to change the actual hardware flags register.

    It is important that the full record be used, not a shorter version of it, since the routine that copies the hardware

    registers into the regrec record assume the full record is available.

    TPLibProc(filename, offset);

    TPLibFunc(filename, offset);

    These procedures load a binary file from the specified filename (a string constant or constant expression) and

    execute the routine at the specified (integer) offset into that file.

    The machine language code contained in the binary file must be position independent.

    Some Turbo Pascal programs (notably those written for version 2.0 of Turbo Pascal) assume only one routine

    per binary file; in this case, use an offset value of zero.

    On entry to a routine called in this way, the return address is on top of the stack, and it is always a one-word

    value (i.e. it is a return address within the current code segment). The routine ends with a RET instruction, which

    also removes the parameters from the stack. The BP register should be preserved (usually by pushing it, and then

    transferring the SP register into BP to allow easy access to variables in the stack frame). Restoring SP from BP

    and then popping BP is a standard way of ending a function.

    If the routine has additional parameters following it in its call, then the following applies:

    - Var type parameters are passed as long pointers (segment address is higher on the stack than the offset). -

    value parameters generally have their actual values pushed onto the stack - integers, chars, bytes, subranges of

    integers and booleans will take a single word, with the top byte set to zero for chars and bytes; - real values are

    stored as six-byte quantities, with the exponent lowest in memory. - strings are stored as the string length,

    followed by the characters in the string in reverse (i.e. right-to-left) order up into the stack. - sets always occupy

    32 bytes (one bit for each member). - pointers are passed much like var parameters, with the word containing

    the segment address higher than the offset. - arrays and records are passed like pointers and var parameters.

  • 7/27/2019 The Pascal Library

    19/19