This is Info file ./gpc.info, produced by Makeinfo version 1.67 from
the input file ./gpc.texi.

   This file documents the use and the internals of the GNU Pascal
compiler.

   Copyright (C) 1988, 1996 Free Software Foundation, Inc.

   Permission is granted to make and distribute verbatim copies of this
manual provided the copyright notice and this permission notice are
preserved on all copies.

   Permission is granted to copy and distribute modified versions of
this manual under the conditions for verbatim copying, provided also
that the sections entitled "GNU General Public License," "Funding for
Free Software," and "Protect Your Freedom--Fight `Look And Feel'" are
included exactly as in the original, and provided that the entire
resulting derived work is distributed under the terms of a permission
notice identical to this one.

   Permission is granted to copy and distribute translations of this
manual into another language, under the above conditions for modified
versions, except that the sections entitled "GNU General Public
License," "Funding for Free Software," and "Protect Your Freedom--Fight
`Look And Feel'", and this permission notice, may be included in
translations approved by the Free Software Foundation instead of in the
original English.


File: gpc.info,  Node: Extended Pascal,  Next: Borland Pascal,  Prev: Extensions,  Up: Top

About Pascal and Extended Pascal languages
******************************************

   Pascal is a well-known programming language and hardly needs to be
described here.  Notice, however, that some people's idea of Pascal is
affected by acquaintance with such products as Turbo Pascal which
differ from the Pascal standard and provide a lot of nonstandard
extensions (some of which are compatible with the Extended Pascal
standard).  Moreover, it is worth mentioning that the ISO Pascal
standard defines two levels of the language, level 0 and level 1; the
only difference between the levels is that level 1 supports the
so-called conformant array schemas in parameter declarations.

   Extended Pascal is a standardized language which contains so
significant extensions to Pascal that it is best regarded as a new
language.  It is currently not very well known, and computer vendors do
not seem to be eager to provide compilers for it.  Thus, there is
social need for GNU Pascal supporting Extended Pascal.

A comparison of Borland Turbo Pascal with Extended Pascal
=========================================================

   As mentioned earlier, Turbo Pascal does not conform to any of the
Pascal standards.  If you carefully chose a subset of unextended
Pascal, you may be able to port code if you're lucky/careful.

   To be fair, Turbo Pascal has some wonderful features that make it
very powerful in the environments in which it runs.  However, some of
those features are of little use on non Windows/DOS platforms and
probably are not good candidates for standardization.

   There are several Turbo Pascal features which are semantically
similar to features in unextended Pascal or Extended Pascal.  Here is a
list of mappings between Turbo Pascal features and Extended Pascal
features:

   * Case constructs

       a. Extended Pascal uses `otherwise' instead of `else'.

          *Borland Pascal*
               case c of
                 'A' : ;
                 'B' : ;
                 else ...;
               end;

          *Extended Pascal*
               case c of
                 'A' : ;
                 'B' : ;
                 otherwise ...;
               end;

       b. Missing cases cause Extended Pascal compilers to halt. In the
          case statement above if you had no `otherwise' clause and
          char c had the value 'C', you got an error (note, this would
          be unnoticed in Borland Pascal).


   * Procedure and function types and variables

     Here is an area of subtle differences.  Turbo Pascal has true
     procedure/function types but doesn't have standard Pascal's
     procedural/functional parameters.

     *Borland Pascal*
          type
            CompareFunction = function(Key1, Key2 : string) : integer;
          
          function Sort(Compare : CompareFunction);
          begin
            ...
          end;

     *Extended Pascal*
          function Sort(Compare : function(Key1, Key2 : string) : integer);
          begin
            ...
          end;

     Moving from Turbo Pascal to Extended Pascal might be difficult if
     the Turbo Pascal program saves, compares, trades, etc. procedure
     values.  For example, an array of procedure values isn't possible
     in Extended Pascal.  Moving the other way is a little easier as
     show by the above examples.

   * Strings

       a. Borland Pascal's string type has a special case, namely
          `string' without a length meaning the same as `string[255]'.
          There is no default in Extended Pascal so you have to change
          all string types to `string(255)'. Example:

               var
                 s : string;

          becomes:
               var
                 s : string(255);

          Note also that you have to use parentheses instead of
          brackets.

       b. A nice pitfall is the pointer to string as in:

               type
                 PString = ^String;

          In Extended Pascal this is a pointer to a schema type! Don't
          forget to translate this to:

               type
                 string255 = string(255);
                 PString = ^string255;

          If you indeed want to use String as a schema pointer you can
          define things like:

               type
                 MyStr : ^String;
               begin
                 New(MyStr, 1024);
               end;

          to allocate 1024 bytes of string space.

       c. As you could see above, Extended Pascal has no 255 byte limit
          for strings. It is however save to assume a limit of about
          32000 bytes. At least Prospero's Extended Pascal limits
          strings to 32760 bytes. GNU Pascal seems to allow larger
          strings.  DEC Pascal limits strings to 65535 bytes.


   * Constant variables

       a. Extended Pascal translates Borland's gruesome:

               const
                 i:integer = 0;

          to:

               var
                 i : integer value 0;

       b. You can also assign initialization values to types. Like:

               type
                 MyInteger = integer value 0;
               
               var
                 i : MyInteger;

          All variables of type MyInteger are automatically initialized
          to 0 when created.

       c. Constant arrays of type string are translated from:

               const
                 MyStringsCount = 5;
               type
                 Ident = string[20];
               const
                 MyStrings : array [1..MyStringsCount] of Ident = (
                               'EXPORT', 'IMPLEMENTATION', 'IMPORT', 'INTERFACE',
                               'MODULE');

          to:

               const
                 MyStringsCount = 5;
               type
                 Ident = string(20);
               var
                 MyStrings : array [1..MyStringsCount] of Ident value [
                   1:'EXPORT'; 2:'IMPLEMENTATION'; 3:'IMPORT';
                   4:'INTERFACE'; 5:'MODULE'];

          There seem to be pros and cons to each style.

          Some folks don't like having to specify an index since it
          requires renumbering if you want to add a new item to the
          middle.  However, if you index by an enumerated type, you
          might be able to avoid major renumbering by hand.


   * Variant records

     The following construction is not allowed in Extended Pascal:
          type
            PersonRec = record
              Age : integer;
              case EyeColor : (Red, Green, Blue, Brown) of
                Red, Green : (Wears_Glasses : Boolean);
                Blue, Brown : (Length_of_lashes : integer);
              end;
            end;

     The variant field needs an explicit type. Code this as:

          type
            EyeColorType = (Red, Green, Blue, Brown);
            PersonRec = record
              Age : integer;
              case EyeColor : EyeColorType of
                Red, Green : (Wears_Glasses : Boolean);
                Blue, Brown : (Length_of_lashes : integer);
              end;
            end;

   * Units

       a. You can translate units almost automatically to Extended
          Pascal Modules, taking into account some differences of
          course.

          Extended Pascal does not automatically export everything named
          in a module, but you have to create seperate export clauses.

          For example translate the following unit:

               unit A;
               
               interface
               
               uses
                 B, C;
               
               procedure D;
               
               implementation
               
               procedure D;
               begin
               end;
               
               end.

          to this module:

               module A interface;
               
               export
                 A = (D);
               
               import
                 B;
                 C;
               
               procedure D;
               
               end.
               
               module A implementation;
               
               procedure D;
               begin
               end;
               
               end.

          You can have one or more export clauses and the name of an
          export clause doesn't have to be equal to the name of the
          module.

          You also see in this example how to translate the Borland
          Pascal "uses" clause to the Extended Pascal "import" clause.

       b. Borland Pascal allows you to have code in a unit that is
          executed once, at startup, to initialize things. You can
          translate this to Extended Pascal's "to begin do ..end"
          structure.

          *Borland Pascal*
               unit A;
               
               interface
               
               implementation
               
               begin
                 { do something }
               end.

          *Extended Pascal*

               module A interface;
               end.
               
               module A implementation;
               
               to begin do begin
                 { do something }
               end;
               
               end.

          Extended Pascal also has a `"to end do .... end"' so you can
          translate `Exit' handlers also.


   * Files

     Extended Pascal treats files quite differently as Borland Pascal.
     I'm not going to treat file pointers, Get and Put here, but
     instead I focus on special Extended Pascal features.

     In Borland Pascal you can read any text file as follows:

          var
            t : text;
            Line : string;
          begin
            Assign(t, 'MYTEXT.TXT');
            Reset(t);
            while not eof(t) do  begin
              readln(t, Line);
              writeln(Line);
            end;
          end;

     The `Assign' function associated the textfile `T' with the file
     `MYTEXT.TXT'.

     In Extended Pascal, files are considered entities external to your
     program. External entities, which don't need to be files, need to
     be bound to a variable your program. Any variable to which
     external entities can be bound needs to be declared bindable. So
     the variable declaration of t becomes:

          var
            t : bindable text;

     Extended Pascal has the bind function that binds a variable with
     an external entity.  Here is an Extended Pascal procedure that
     emulates the Assign procedure in Turbo Pascal.

          procedure Assign(var t : text; protected Name : string);
          var
            b : BindingType;
          begin
            unbind (t);
            b := binding (t);
            b.Name := Name;
            bind (t, b);
            b := binding (t);
          end;

     Comments: the unbind procedure unbinds a bindable variable from
     its external entity. If it is not bound, nothing happens. The
     binding function initializes b. We call binding to set some fields
     of the BindingType record. Next we set the name field to the name
     of the file. Calling bind will bind t to the external entity. If
     we now call binding again, we get the current state of t's binding
     type. We can now check for example if the bind has succeeded by:

          if not b.bound then
            { do error processing }

     Note that Prospero's Pascal defaults to creating the file if it
     does not exists! You need to use Prospero's local addition of
     setting `b.existing' to `true' to work-around this.

     I've not worked with binary files enough, so no advice yet on how
     to access them, but you access them much the same.

     As last an example of getting the size of a file.

          function FileSize(filename : String) : LongInt;
          var
            f : bindable file [0..MaxInt] of char;
            b : BindingType;
          begin
            unbind(f);
            b := binding (f);
            b.Name := filename;
            bind(f, b);
            b := binding(f);
            SeekRead(f, 0);
            if empty(f)
              then  file_size := 0
              else  file_size := LastPosition(f) + 1;
            unbind(f);
          end(*file_size*);

     Prospero's Extended Pascal has a bug in this case. Replace the
     MaxInt in the type definition of f by a sufficiently large
     integer. GNU Pascal works correct in this case.


File: gpc.info,  Node: Borland Pascal,  Next: FPK Pascal,  Prev: Extended Pascal,  Up: Top

From Borland Pascal to GNU Pascal
*********************************

   This chapter is intended to be a QuickStart guide for programmers
who are familiar with Borland Pascal, version 7 for DOS protected mode.
Other versions don't differ too much but this one is the very last DOS
version Borland has published.

* Menu:

* Borland compatibility::
* There is no IDE!::
* Comments and compiler directives::
* Units; GPI files and AutoMake::
* Optimization::
* Debugging::
* GPC inline assembler::
* Objects::
* Strings::
* Typed constants::
* Bit; byte and memory manipulation::
* User-defined operators::
* Data types::
* Files::
* Built-in constants::
* Built-in operators::
* Built-in Procedures and Functions::
* Parameters::
* Miscellaneous::


File: gpc.info,  Node: Borland compatibility,  Next: There is no IDE!,  Up: Borland Pascal

Borland compatibility
=====================

   Unlike other FreeWare compilers, GNU Pascal is *not* intended to be
100% Borland compatible.  GNU Pascal is part of the GNU project, so
portability is one of its primary goals.  For this reason, non-portable
features of Borland Pascal will probably not be included into GNU
Pascal.  Some other differences are so minimal that we have more
important things to do than to implement them.

   However if you want to contribute to GNU Pascal by eliminating holes
in GPC's Borland compatibility, be welcome in the GNU Pascal
development team!  See *Note How to Contribute:: for details.


File: gpc.info,  Node: There is no IDE!,  Next: Comments and compiler directives,  Prev: Borland compatibility,  Up: Borland Pascal

There is no IDE!
================

   It is one of the most annoying points about GPC that there is no
Integrated Development Environment like BP.EXE at the moment.  We are
working on it, but this will take some time, especially because GNU
Pascal is a *portable* compiler intended to run under a large variety
of operating systems in the same manner.  Please be patient--or offer
your help!  (For the moment, you can try to use Borland's IDE for GNU
Pascal--see below.)

   The GNU Pascal Compiler, GPC, is called about like the command-line
version of the Borland Pascal Compiler, BPC.  Edit your source file(s)
with your favorite ASCII editor (e.g. the Borland IDE), then call GNU
Pascal with a command line like

       C:\GNU-PAS> gpc hello.pas -o hello.exe

on your DOS or OS/2 box (with EMX you may omit the `-o ...') or

       myhost/home/joe/gnu-pascal> gpc hello.pas -o hello

on your UNIX (e.g. Linux) box.  Don't omit the suffix `.pas':  GPC is a
common interface for a Pascal compiler, a C, ObjC and C++ compiler, an
assembler, a linker, and perhaps a Modula and FORTRAN compiler.  From
the extension of your source file GPC figures out which processor to
run.

   The `-o' is a command line option which tells GPC how the executable
has to be named.  This is not necessary for DOS and OS/2, so we omit it
in this file from now on.

   Note that GPC is case-sensitive concerning file names, so it will
*not* work if you type

       C:\GNU-PAS> GPC HELLO.PAS -O HELLO.EXE

   GPC is a very quiet compiler and doesn't print anything on the
screen unless you request it or there is an error.  If you want to see
what is going on, invoke GPC with additional options:

       -Q            "don't be quiet"  (or: Quassel-Modus in German)

(with *capital* `Q'!) means that GPC prints out the names of procedures
and functions it processes, and

       --verbose

means that GPC informs you about the stages of compilation, i.e.
preprocessing, compiling, assembling, and linking.

   One example (this time for OS/2):

       [C:\GNU-Pascal] gpc --verbose -Q hello.pas

   Throughout this chapter, we will tell you about a lot of
command-line switches.  They are all invoked this way.

   After compilation, there will be an executable `hello' file in the
current directory.  (`hello.exe' with DOS and OS/2.)  Just run it and
enjoy.  If there are errors, GNU Pascal will not stop compilation after
the first one--as Borland Pascal does--but try to catch them all in one
compilation.  If you get more error messages than your screen can hold,
you can catch them in a file (e.g. `gpc.out') in the following way:

       gpc hello.pas 2>gpc.out

   This works with OS/2 and any bash-like shell under UNIX; for DOS you
must get a replacement for `command.com' which supports this kind of
redirection (see also the DJGPP FAQ).

   You can also use Borland's IDE for GNU Pascal on the DOS platform:
Install the GNU Pascal Compiler in the Tools menu (via Options/Tools).

       Name:       GNU Pascal
       Path:       gpc
       Arguments:  $SAVE ALL --verbose -Q $NAME($EDNAME).pas
       HotKey:     Shift+F9

   Note once more that GPC is case-sensitive, so it is important to
specify `.pas' instead of the `.PAS' Borland Pascal would append
otherwise!

   You can include more command-line arguments to GNU Pascal (e.g.
`--automake'; see below) as you will learn more about them.

   Since Borland Pascal will try to recompile your program if you use
its `run' menu function, you will need another "tool" to run your
program:

       Name:       run program
       Path:       command.com
       Arguments:  /c $NAME($EDNAME)
       HotKey:     Shift+F10


File: gpc.info,  Node: Comments and compiler directives,  Next: Units; GPI files and AutoMake,  Prev: There is no IDE!,  Up: Borland Pascal

Comments and compiler directives
================================

   According to ISO 7185 and ISO 10206 standard, GNU Pascal recognizes
by default comments opened with `(*' and closed with `}'.  With Borland
Pascal, both types of comments can be nested, so you will probably have
sources where passages containing comments are "commented out".

   To use this with GPC, you have to "switch on" nested comments either
by a command-line option, or by a compiler directive:

       --nested-comments            {$N+}    (*$N+*)

   The $N directive also exists in BP but has another meaning.  The
same holds for most of GPC's other compiler directives (also
corresponding to command-line options in most cases):

       --short-circuit     $B+ $B-  like in Borland Pascal:
                                    $B- means short-circuit Boolean
                                    operators; $B+ complete evaluation
     
       --c-numbers         $C+ $C-  enable/disable C-style octal 0177
                                    and hexadecial 0xFF numbers
     
       --char-escapes      $E+ $E-  enable/disable C-style character
                                    escape sequences in strings
     
       --nested-comments   $N+ $N-  see above
     
       --pedantic          $P+ $P-  give/don't give warnings about
                                    violations of ISO 7185
                                    Standard Pascal
     
                           $W+ $W-  enable/disable warnings
     
                           $X+ $X-  enable/disable extended syntax
                                    (function return value ignore,
                                    operator definitions)
     
       {$I FileName }               include filename.pas or
                                    filename.p (make it lowercase)
     
       {$include "filename.pas"}    include (case-sensitive)
     
       {$include <filename.pas>}    the same, but don't search in
                                    current directory
     
       {$M Hello!}                  write message "Hello!" to error
                                    device during compilation
     
       {$D GNU}                     define GNU (for conditional
       {$define GNU}                compilation)
     
       -D GNU                       the same in command line
     
       {$D loop while true do}      define "loop" to be "while
                                    true do" as a macro like in C.
                                    It is case-sensitive.
     
       {$ifdef GNU}                 conditional compilation
         ...                        (like in Borland Pascal).
       {$else}                      GPC predefines the symbol
         ...                        __GPC__ (with two leading
       {$endif}                     and trailing underscores).

   You also can use C-style preprocessor directives, e.g. #include.

   As in Borland Pascal, `{$...}' and `(*$...*)' are equivalent.


File: gpc.info,  Node: Units; GPI files and AutoMake,  Next: Optimization,  Prev: Comments and compiler directives,  Up: Borland Pascal

Units, GPI files and AutoMake
=============================

   You can use Units in the same way as in Borland Pascal.  However,
there are some differences, problems and new features.  (Please report
the bug if something doesn't work.)

   Concerning the syntax of a Unit, you can, if you want, use Extended
Pascal syntax to specify a Unit initializer, i.e.  instead of writing

       begin
         ...
       end.

at the end of the Unit, you can get the same result with

       to begin do
         begin
           ...
         end (* to begin *);

and there also exists

       to end do
         begin
           ...
         end (* to end *);

   which specifies a finalization routine.  Use this instead of Borland
Pascal's exit procedures.  You also can specify an order in which
initializers are run--see *Note Extensions:: and *Note Extended
Pascal:: for more about this.  There you can also find information
about Extended Pascal Modules, an alternative to Units.

   At the moment, there are no qualified identifiers, so take care
about name clashes between different Units.

   When GPC compiles a Unit, it produces two files: an `.o' object file
(compatible with other GNU compilers such as GNU C) plus a precompiled
Interface which resides in a `.gpi' file.  (See *Note GPI files:: for
GPI file internals.)

   GPC does not automatically recognize that something is a Unit and
cannot be linked; you have to tell this by a command line switch:

       -c            only compile, don't link.

   For example, to compile two units, use:

       gpc -c myunit1.pas myunit2.pas

   Of course, one of the purposes of writing Units is to compile them
separately.  However, GNU Pascal allows you to have one or more Units
in the same source file (producing only one `.o' file but separate
`.gpi' files).  You even can have a Program and Units in one and the
same source file; in this case, no `.o' file is produced at all.

   You can use the above as a workaround (*$include the Unit *) in case
something goes wrong with the .gpi mechanism.  (It is a new feature in
GPC 2.0 and may be unstable.)

   When you have all Units compiled and want to compile the Program,
specify the `.o' files in the command line:

       gpc hallo.pas myunit1.o myunit2.o

   You also can specify the program and the units in one command line:

       gpc hallo.pas myunit1.pas myunit2.pas

   As an alternative to manually compiling and specifying object files,
you can use GPC's AutoMake feature.  (WARNING: This is a new feature in
GPC 2.0 and may be unstable!)  With an additional command-line argument

       gpc --automake hallo.pas

   GPC tries to behave like Borland Pascal's `make' facility and
automatically recompiles Units the source of which has been changed.
It also works if an included file has been changed.

   To pass arguments to the compilation of Units, specify them in a
string surrounded by quotation marks after `--automake='.  For example,
if you want to give the `--verbose' argument not only at top level but
also for (re)compilation of Units, use:

       gpc --verbose --automake="--verbose" hallo.pas

   For more information about the AutoMake mechanism, see *Note
AutoMake::.


File: gpc.info,  Node: Optimization,  Next: Debugging,  Prev: Units; GPI files and AutoMake,  Up: Borland Pascal

Optimization
============

   GNU Pascal is a 32 bit compiler with excellent optimization
algorithms (which are identically the same as those of GNU C).  There
are three optimization levels, specified by the command line options
`-O', `-O2', and `-O3'.  (Levels up to `-O6' are worked on.)

   One example:

       Program Test;
     
       Var
         A, B: Integer;
     
       begin
         A:= 3;
         B:= 4;
         writeln ( A + B );
       end.

   When GNU Pascal compiles this program with optimization, it
recognizes that the argument of writeln is the constant 7--and
optimizes away the variables `A' and `B'.

   For more about optimization, see the GNU C documentation.


File: gpc.info,  Node: Debugging,  Next: GPC inline assembler,  Prev: Optimization,  Up: Borland Pascal

Debugging
=========

   The command line option `-g' specifies generation of debugging
information for GDB, the GNU debugger.  GDB is not as comfortable as the
Turbo Debugger, but it has the same abilities but one:  The program
being debugged is slowed down.  For more information about GDB, call it
(with `gdb') and type in the `help' command.

   GDB has one very nice feature which might even make up for the
slowing-down problematic:  When a GNU-compiled program crashes, it puts
out a `core' file.  When you say "target core core" to the GNU
debugger, it reads the core file and can tell you the address of the
crash, the contents of variables and of the stack, and so on.

   Sometimes it is nice to have a look at the assembler output of the
compiler.  When you specify the `-S' command line option, GPC produces
an `.s' file instead of an `.o' file which contains assembler source
for your program.  More about this in the next section.


File: gpc.info,  Node: GPC inline assembler,  Next: Objects,  Prev: Debugging,  Up: Borland Pascal

GPC inline assembler
====================

   GNU Pascal has an inline assembler, but it is quite different from
Borland's one.  I have not yet found reasonable documentation about the
use of this assembler, but I found out the following:

   The syntax is

       asm ( 'movl $12345678, %eax' );
       asm ( 'movl %eax, %edx' );

   to move the (hex) value `$12345678' to the EAX register and then to
the EDX register.  The String argument of the asm "procedure" is passed
as a string to the assembler stage of the compilation.  The assembler
follows the AT&T, not the Intel syntax.  Note that the order of
operands is reversed with respect to the order you know from Intel
assemblers and that the size of the arguments is appended to the
mnemonic as a suffix b (byte), w (word = 2 bytes), or l (long = 4
bytes).

   You can learn about the GNU assembler syntax when compiling your
program with `-S' (see above) and looking into the resulting assembler
source.

   To access Pascal symbols from the assembler, do something like

       asm ( 'movl %%eax, %0' : : 'rm' ( MyVariable ) );

   Here, the % signs in front of the register names are doubled because
% gets some special meaning.  The 'rm' means that the operand may be in
a register or in memory.

   (If somebody knows more about the GNU assembler syntax, please,
please, please explain it to me or point me to some reasonable
documentation about it! <peter.gerwinski@uni-essen.de>)


File: gpc.info,  Node: Objects,  Next: Strings,  Prev: GPC inline assembler,  Up: Borland Pascal

Objects
=======

   Objects in the Borland Pascal 7.0 notation are implemented into GNU
Pascal with the following differences:

   * the "private" directive does not work,

   * data fields and methods may be mixed:
            MyObj = object
              x: Integer;
              Procedure Foo; virtual;
              y: Real;
              Function Bar: Char;
            end (* MyObj *);


File: gpc.info,  Node: Strings,  Next: Typed constants,  Prev: Objects,  Up: Borland Pascal

Strings
=======

   Strings are "Schema types" in GNU Pascal which is something more
complicated than Borland-style strings.  For variables, you cannot
specify just `String' as a type (always specify the maximum length);
for parameters you can.  There is no 255 length limit.  According to
Extended Pascal, the maximum string length must be in (parantheses);
GNU Pascal accepts [brackets], however.

   For more about Strings and Schema types see *Note Extensions:: and
*Note Extended Pascal::.

   String-handling functions (see *Note Extensions::) are different in
both dialects but can approximately be mapped on each other:

       Borland Pascal          GNU Pascal
     
       length                  length
       Pos                     Index
       Str                     WriteStr
       Val                     ReadStr
       Copy                    SubStr, MyStr [ 2..7 ]
       MyStr [ 0 ]:= #7;       Trim
         -                     EQ, NE, LT, LE, GT, GE
       Insert                    -
       Delete                    -

   It should not be difficult to write a compatibility Unit--if you do
so, please send it to us!


File: gpc.info,  Node: Typed constants,  Next: Bit; byte and memory manipulation,  Prev: Strings,  Up: Borland Pascal

Typed constants
===============

   GNU Pascal supports Borland Pascal's "typed constants" but also
Extended Pascal's initialized variables:

       Var
         x: Integer value 7;

   When a typed constant is misused as an initialized variable, a
warning is given.

   Initialization of structured variables (typed constants) is not yet
stable.

   When you want a local variable to preserve its value, define it as
`__static__' instead of using a typed constant:

       Procedure Foo;
     
       Var
         x: __static__ Real;
     
       begin (* Foo *)
         (* x keeps its value between two calls to this Procedure *)
       end (* Foo *);

   Remark: If you don't like underscores, you can use the (*$define *)
mechanism to get rid of them:

       (*$define static __static__ *)


File: gpc.info,  Node: Bit; byte and memory manipulation,  Next: User-defined operators,  Prev: Typed constants,  Up: Borland Pascal

Bit, byte and memory manipulation
=================================

   The (non-standard) bitwise operators `shl', `shr', `and', `or',
`xor' work in GNU Pascal like in Borland Pascal.  As an extension, you
can use them as "procedures", for examples

       and ( x, $0000FFFF );

   as an alternative to

       x:= x and $0000FFFF;

   Instead of the Borland-specific notation `$ABCD' for hexadecimal
numbers you also can use Extended Pascal notation:

        2#11111111   for a binary,
        8#177        for an octal,
       16#FF         for a hexadecimal number,

   and so on up to a basis of 36.

   Inc and dec are implemented like in Borland Pascal; pred and succ
are generalized according to Extended Pascal:

       a:= succ ( a, 5 );

   Absolute variables work only in the context of overloading with
other variables, not in the context of specifying an absolute address.
The Mem and Port arrays don't exist in GNU Pascal.

   Borland Pascal's procedures `FillChar' and `move' are not built-in
into GNU Pascal.  However, you can write them by yourself using untyped
Var parameters (see Sec. `Data types').


File: gpc.info,  Node: User-defined operators,  Next: Data types,  Prev: Bit; byte and memory manipulation,  Up: Borland Pascal

User-defined operators
======================

   GNU Pascal allows the user to define operators according to the
Pascal-SC syntax:

       (*$X+*)
     
       Type
         Point = record
           x, y: Real;
         end (* Point *);
     
       Operator + ( a, b: Point ) c: Point;
     
       begin (* Point + Point *)
         c.x:= a.x + b.x;
         c.y:= a.y + b.y;
       end (* Point + Point *);

   It is necessary to enable "extended syntax" `(*$X+*)' when defining
operators.

   The Pascal-SC operators `+>', `+<', etc. for exact numerical
calculations are not implemented, but you can define them.  If you
write a module which really implements these operators, please send it
to us, so we can include it into the next distribution.

   (And if you know more about modules in Pascal-SC than just their
existence, please contact us either!  We could probably easily
implement them if we knew how they look like.  Something quite close to
Pascal-SC modules already *is* implemented as "GNU specific modules".)


File: gpc.info,  Node: Data types,  Next: Files,  Prev: User-defined operators,  Up: Borland Pascal

Data types
==========

   * Generic Pointer:  There is no built-in untyped Pointer in GNU
     Pascal.  Use `^Void' to define it.

   * Integer types:  There is no built-in Byte, Word, etc. in GNU
     Pascal.  Use the modifiers `__byte__', `__short__', `__long__' and
     `__unsigned__' (described in *Note Extensions::) to define them.

            Borland Pascal          GNU Pascal
          
            shortint                __byte__ Integer
            Integer                 __short__ Integer
            LongInt                 Integer = __long__ Integer
            Comp                    __longlong__ Integer
            Byte                    __unsigned__ __byte__ Integer
            Word                    __unsigned__ __short__ Integer
              -                     __unsigned__ __long__ Integer
              -                     __unsigned__ __longlong__ Integer

     Real types: There is no built-in `Single', `Double', `Extended' in
     GNU Pascal; Real has 8 bytes on an Intel-x86 machine.  Use
     `__short__ Real' to define `Single', `__long__ Real' to define
     `Extended'.

            Borland Pascal          GNU Pascal
          
            Single                  __short__ Real
            Real                      -
            Double                  Real
            Extended                __long__ Real
            Comp                    __longlong__ Integer

     A KNOWN BUG:  You cannot `writeln' variables of a type with a `__'
     modifier.  To work around, cast them to their basis type (Integer
     or Real) when `writeln'ing them:

            Var
              x: __long__ Real;
          
            writeln ( Real ( x ) );

   * Complex numbers:  According to Extended Pascal, GNU Pascal has
     built-in complex numbers.

   * Record types: GNU Pascal alignes 32-bit fields on 4-byte addresses.
     Thus the record
            Type
              myRec = record
                f, o, oo: Boolean;
                Bar: Integer;
              end (* myRec *);
     has 8 bytes, not 7.

   * Instead of procedural types, GNU Pascal has pointers to procedures:

              Type
                FuncPtr = ^Function ( Real ): Real;

     Furthermore, GNU Pascal supports Standard Pascal's procedural
     parameters--see below.


File: gpc.info,  Node: Files,  Next: Built-in constants,  Prev: Data types,  Up: Borland Pascal

Files
=====

   * GNU Pascal no built-in `Assign' procedure for files, but you can
     write it by yourself using the "Bind" mechanism of Extended Pascal:

            Procedure Assign ( Var T: Text; Name: String );
          
            Var
              B: BindingType;
          
            begin (* Assign *)
              unbind ( T );
              B:= binding ( T );
              B.Name:= Name;
              bind ( T, B );
              B:= binding ( T );
            end (* Assign *);

   * GNU Pascal has no untyped files, "BlockRead", or "BlockWrite".


File: gpc.info,  Node: Built-in constants,  Next: Built-in operators,  Prev: Files,  Up: Borland Pascal

Built-in constants
==================

   * Pi constant:  not built-in.  Use Pi = 3.14159265358979323846.

   * Other built-in constants:  GNU Pascal has `MaxInt', `MaxChar',
     `MaxReal', and `MinReal', but no `MaxLongInt'.


File: gpc.info,  Node: Built-in operators,  Next: Built-in Procedures and Functions,  Prev: Built-in constants,  Up: Borland Pascal

Built-in operators
==================

   * Exponentiation:  According to Extended Pascal, GNU Pascal supports
     exponentiation operators `pow' and `**' which do not exist in
     Borland Pascal.  You can use `x pow y' for integer and `x ** y'
     for real or complex exponents; the basis may be integer, real or
     complex in both cases.

   * Address operator: GNU Pascal accepts Borland's `@', but also `&'
     as an address operator.

   * GNU Pascal has a symmetric set difference operator `set1 >< set2'.
     See *Note Extensions:: for more about this.


File: gpc.info,  Node: Built-in Procedures and Functions,  Next: Parameters,  Prev: Built-in operators,  Up: Borland Pascal

Built-in Procedures and Functions
=================================

   * `Write' and `writeln' default behaviour:  The numeric default
     format of "write" and "writeln" differs between both Pascal
     dialects.  The standard format of GNU Pascal is a field of length
     14 for real, and a field of length 10 for integer values, while
     Borland Pascal begins just left by default.  An explicit
     fieldlength of zero causes GNU Pascal to omit the output; in
     Borland Pascal it yields the default.

   * `GetMem' and `FreeMem':  `GetMem' can also act as a function in
     GNU Pascal:

            p:= GetMem ( 1024 );

     The second parameter to FreeMem is ignored by GNU Pascal and may
     be omitted.  Memory blocks are always freed with the same size
     they were allocated with.

     Remark:  Extended Pascal Schema types will provide a cleaner
     approach to most of the applications of `GetMem' and `FreeMem' in
     the future.

   * `Min' and `max':  GNU Pascal has built-in `min' and `max'
     functions (two arguments) which work for all ordinal types
     (`Integer', `Char', ...) plus `Real'.

   * `UpCase' function:  not built-in.

   * `Lo', `Hi', `Swap' functions:  not built-in.


File: gpc.info,  Node: Parameters,  Next: Miscellaneous,  Prev: Built-in Procedures and Functions,  Up: Borland Pascal

Parameters
==========

   * Untyped Var parameters can be denoted by

            Procedure Foo ( Var x );

     like in Borland Pascal.  In GNU Pascal, you can also use

            Procedure Foo ( Var x: Void );

   * GNU Pascal defines "ellipsis" parameters vor variable argument
     lists,

            Procedure Foo ( a: Integer; ... );

     but does not (yet) provide a portable mechanism to access the
     additional arguments.

   * Structured function return values:  According to Extended Pascal,
     GNU Pascal allows structured function return values.

   * Open array parameters
            Procedure Foo ( a: array of Integer );
     are implemented.  However, Standard Pascal conformant array
     parameters (only partially implemented) are a "cleaner" mechanism
     to pass arrays of variable size.

   * GNU Pascal supports Standard Pascal's procedural parameters:

            Procedure DrawGraph ( f: Function ( Real ): Real );


File: gpc.info,  Node: Miscellaneous,  Prev: Parameters,  Up: Borland Pascal

Miscellaneous
=============

   * Headlines:  According to Extended Pascal, a Program headline must
     contain the program's parameters:

              Program Foo ( Input, Output );

     In GNU Pascal, headline parameters are optional.  If the headline
     is omitted, a warning is given.

   * Case statements:  In a case statement, GNU Pascal has `otherwise'
     as an alternative to `else' (according to Extended Pascal):

            case x of
              1: writeln ( 'one' );
              2: writeln ( 'two' );
              otherwise: writeln ( 'many' );
            end (* case *);

     If there are two ore more statements following `otherwise', they
     must be grouped with `begin' and `end'.

   * Char constants: Chars like `#13' or `^M' are not implemented into
     GNU Pascal.

   * Sets: GNU Pascal has a `card ( myset )' function for sets which
     counts their elements.

   * Inline:  GNU Pasccal allows "inline" Procedures and Functions,
     while Borland Pascal only allows machine code to be inline:

     Borland Pascal:

            Function Max ( x, y: Integer ): Integer;
            Inline ( $58 / $59 / $3B / $C1 / $7F / $01 / $91 );

     GNU Pascal:

            Inline Function Max ( x, y: Integer ): Integer;
          
            begin (* Max *)
              if x > y then
                Max:= x
              else
                Max:= y;
            end (* Max *);

     (Actually, a more general Max is already built-in.)

     This feature is not so important as it might seem because in
     optimization level 3 (see above), GNU Pascal automatically
     "inlines" short Procedures and Functions.


File: gpc.info,  Node: GPC Bugs,  Next: How to Contribute,  Prev: FPK Pascal,  Up: Top

Known bugs and inconveniences; how to report bugs
*************************************************

   The GNU Pascal Compiler (GPC) does not yet implement the whole ISO
10206 Extended Pascal standard, not even the whole ISO 7185 Pascal
standard.  It is only partially compatible to Borland Pascal and
implements only some isolated features from the PXSC standard.
Furthermore, there are *lots* of known bugs which will take a long time
to be fixed.  (Any help welcome!)  Please take this into account when
you consider using GPC for any purpose.

   If you encounter a bug with GPC, please check whether it is one of
the known bugs.  If not, report it to the GNU Pascal mailing list
`gpc@hut.fi'.  (But always report it if you solve the problem! ;-)

General bugs
============

   * High optimization levels do not work properly on the Alpha.  Some
     conformance tests *fail* when compiled with `-O6' flag, which
     means that the compiler generates invalid code. Don't use this
     flag in the Alpha before the problem gets fixed.  It might have
     something to do with automatic inlining, but I have not yet looked
     at this. `-O' flag should be ok.  (Also take care when using
     explicit inline functions.)

   * Run time errors are not checked.

   * For some reason the pascal main program does not get lineno stabs,
     so it is hard to debug it with `gdb' ...

   * Modules and Units export everything, not just the stuff in the
     export interfaces.  However, the unexported variables and
     functions are invisible to modules *in other files*.

     *Workaround:* Put each Module or Unit in its own source file and
     compile it separately.

   * The `GPI' mechanism crashes when compiling some Modules, for
     example the `System' module by Berend de Boer.

     *Workaround:* Include the Unit or Module into the main program's
     source:
            (*$I MyModule *)
          
            Program MyProg;
          
            uses
              MyModule;
          
            ...

   * When `gpc' is invoked for linking only, it crashes on some systems.

     *Workaround:* Use `gcc' instead of `gpc' for linking:
            gpc -c hello.pas
            gcc -o hello hello.o -lm -lgpc

   * Temporary `.gpc' files are not removed after compilation.

   * The inline set operations have some problems with operations on
     two sets if the sets do not contain equally many segments.

   * In addition, the set code generated in the Alpha causes runtime
     errors in the generated code.

   * There are some bugs with mathematical functions.  GPC fails, for
     example, the "Paranoia" test.

   * The main program name is not capitalized.  It may clash with libc
     identifiers which may be important but invisible for the program,
     e.g.  `log'.

Standard Pascal
===============

   * Type checking is mostly what C does, not what Pascal requires, so
     GPC does not yet implement a strongly typed language.  Although
     correct programs compile, incorrect ones compile also.

   * Conformant arrays don't yet work (in general).  Until they do, GPC
     is a Level-0 Standard Pascal compiler.

Extended Pascal
===============

   * Schema types are not yet implemented; only String schemas work
     (well ... sometimes).

   * String schemas as formal value parameters do not work.

     *Workaround:* Pass string types with specified capacity instead,
     i.e. use
            Type
              WrkString = String ( 80 );
          
            Procedure Foo ( S: WrkString );
     instead of
            Procedure Foo ( S: String );

   * Initialized Strings and structured variables are not yet
     implemented.

   * Illegal substrings let crash the compiler rather than triggering an
     error message:
            str:='1234567890';
            i:=8; j:=13;
            str:=str[i..j];

   * The `Index' function does not work when the pattern is a char:
            Var
              C: Char;
              S: String ( 80 );
              i: Integer;
          
            ...
          
            i:= Index ( s, c );  (* "i" always zero *)
     It works with `Var C: String ( 1 );'

Borland Pascal
==============

   *Note Borland Pascal::QuickStart Guide for Borland Pascal users.

   * Strings are implemented in a completely different way.  They are
     not limited to 255 characters with the length being in position
     zero, but they are "Schema types" which is something more
     complicated.

   * Most of Borland Pascal's System Unit is not implemented, e.g.
     `Byte', `Pointer', `LongInt', `move', `FillChar', `BlockRead',
     `BlockWrite', `Assign', String-related functions, ...

     *Workaround:* Some of the missing data types, procedures and
     functions are implemented in a separate compatibility Unit.  Check
     the `contrib' subdirectory of your GPC distribution.

   * Initialized Strings are not yet implemented; initialized structured
     variables do not yet work in all cases.

   * Chars like `#13' or `^M' do not work.  Use `chr ( 13 )' instead.

   * The inline assember does not follow Borland syntax.

   * There is no `private' directive for Objects yet.

   * There are no "Procedural types" but *pointers* to procedures
     instead.

   * There is no `Inline' in Borland sense.

GNU Extensions
==============

   * The Run Time System (RTS) does not know about modified types such
     as `__byte__' or `__unsigned__ Integer's or `__long__ Real's.
     Especially, you cannot `writeln' such variables.

     *Workaround:* Cast them to their basis type before `writeln', e.g.
            Type
              Extended = __long__ Real;
          
            Var
              foo: Extended;
          
            [...]
          
            writeln ( Real ( foo ) );

Inconveniences
==============

   * `New' and `Dispose' optional tag field arguments are ignored
     (warning given, code works).

   * `Gdb' does not yet understand pascal sets, files or subranges.  Now
     `gdb' allows you to debug these things, even though it does not yet
     understand some stabs.

   * `Packed' does not pack. (Implementation dependent, warning given,
     code works.)

   * Files of integer subranges that would fit in a byte do not;
     instead they are handled as files of integer.  This is especially
     annoying with `file of 0..255'.

Notes for debugging
===================

   * Forward referencing pointers generate `dbx' style debugging symbols
     by outputting the `.stabs' as an unknown pointer and later it just
     outputs the same `.stabs' again, but this time it also tells what
     type the pointer points to.  This seems to work for `gdb'. As of
     this writing I have not checked what happens with `sdb' type
     debugging info.  It might be that the pointer is left to be a
     `(void *)' pointer, so you have to cast it in order to output the
     object the pointer points to.

     Also, we have not tried any other debugger than `gdb'.  If you do,
     please let us know what happens.

     I think that GDB does not yet support the kind of `.stabs' that
     should be used to do this correctly:

            .stabs ":tANUMBER=BNUMBER", WHATEVER

     where ANUMBER is the unknown pointer type referenced earlier, and
     the BNUMBER is the type which ANUMBER actually is.  This construct
     is not required in C.

   * When debugging, please note that the Initial Letter In Each
     Identifier Is In Upper Case And The Rest Are In Lower Case.  If
     you wish to call C-routines declare them with the "C" directive,
     as follows:

          Procedure FooBAR(i:integer);c;

     This makes the external name to be `_foobar' (replace `_' with you
     machine prefix.)

          Procedure FooBAR(i:Integer); External;

     Uses external name `_Foobar'.

     It is done like this to reduce name clashes with `libc.a' and
     other possible libraries.

   * All visible GPC runtime system library routines are named `_p_...'.

   * However, the main program name is not capitalized.  (This is a
     kludge; see above.)

