p2c - Pascal to C translator, version 1.21alpha-07.Dec.93


SYNOPSIS

       p2c [ options ] [ file [ module ] ]


DESCRIPTION

       P2c is a tool for translating Pascal programs into C.  The
       input consists of a set of source files in any of the fol­
       lowing  Pascal dialects: HP Pascal, Turbo/UCSD Pascal, DEC
       VAX Pascal, Oregon Software Pascal/2,  Macintosh  Program­
       mer's  Workshop Pascal, Sun/Berkeley Pascal, Texas Instru­
       ments Pascal, Apollo Domain Pascal.   Modula-2  syntax  is
       also  supported.   Output is a set of .c and .h files that
       comprise an equivalent program in any of several  dialects
       of  C.  Output code may be kept machine- and dialect-inde­
       pendent, or it may be targeted to a specific  machine  and
       compiler.   Most  reasonable Pascal programs are converted
       into fully functional C which will compile and run with no
       further  modifications,  although p2c sometimes chooses to
       generate readable code at the expense of absolute general­
       ity.   P2c  endeavors to insert notes and warning messages
       into the output code to point out areas which may  require
       human  intervention.   Output code is arranged to be read­
       able and efficient, and to make use of C  idioms  wherever
       possible.   The main goal of the translation is to produce
       C files which are pleasant  and  "natural"  enough  to  be
       acceptable  as  the  new source files for a program.  In a
       pinch, p2c will also serve as an ad hoc  Pascal  compiler.
       The p2cc(1) script makes it easy to use p2c as a compiler.

       Code generated by p2c normally does not assume  characters
       are  signed or unsigned.  Also, it assumes int is the same
       as either short or long but  does  not  depend  on  which.
       However,  if int is not the same as long it is best to use
       a modern C compiler which supports prototypes.   Generated
       code  does not require an ANSI-compatible compiler (unless
       ANSI-style code is requested), but  it  does  use  various
       ANSI-standard library routines.

       All  generated code includes the file <p2c/p2c.h> which in
       turn  includes  <stdio.h>   and   various   other   common
       resources.  Also, many translated programs will need to be
       linked with the run-time library, typically -lp2c.

       Given a file name, p2c reads from the specified  file  and
       outputs  to  a file with a .c suffix added or substituted.
       For example,

            p2c myfile.pas

       reads from myfile.pas to produce the file  myfile.c.   The
       input  file  may contain a Pascal main program or a single
       Pascal  module  (or  "unit"  in  Turbo  and  UCSD   Pascal

       dures and declarations.  P2c is designed to work for  cor­
       rect input programs.  That is, it will accept partial pro­
       grams but may occasionally core dump if the  input  refers
       to undefined symbols.

       If the input is a module, the translator will also produce
       a file module.h containing a translation of  the  module's
       interface  section.   The  implementation  section  may be
       omitted in which case only the .h file will  be  interest­
       ing.   If  the  program or module has include files, these
       may cause additional .c files to be generated depending on
       the value of the ExpandIncludes option (see below).

       If  no file name is given, p2c reads Pascal from the stan­
       dard input and writes the resulting C to  standard  output
       (though  a .h file may still be produced).  If a file name
       and module name are given, the file  may  include  several
       modules  (or  units).  The specified module is translated;
       any others are skipped.  The output files  will  be  named
       module.c and module.h.  P2c never translates more than one
       module per run.

       Before starting, p2c reads the file /usr/lib/p2c/p2crc for
       a  number  of  configuration parameters.  (The actual path
       used on your system may vary.  The -i option  is  a  handy
       way to examine this file.)  If the P2CRC environment vari­
       able is set, it gives the name of a file to  read  instead
       of  the  system  file;  this  file  can start with Include
       %H/p2crc to include the system file.  Next,  p2c  attempts
       to  read the file p2crc in your directory for further con­
       figuration.  If this file does not exist,  p2c  looks  for
       .p2crc instead.


OPTIONS

       -o cfile
              Use  cfile  in  place  of file.c or module.c as the
              primary output file.  A single dash (`-o  -')  says
              to write the C code to the standard output.

       -h hfile
              Use  hfile  in place of module.h as the output file
              for interface text.  This only has  effect  if  the
              input  is  an  HP  Pascal  module or a Turbo Pascal
              unit.

       -s sfile
              Read interface text from sfile before beginning the
              translation.   This  file typically contains one or
              more modules, often  with  implementation  sections
              omitted  for  speed,  which  the  program or module
              being translated will use.  (Typically the  Import­
              From  and  ImportDir parameters in p2crc are set up
              to allow  p2c  to  locate  interface  text  without

              options in the command, the sfiles  are  read  from
              left to right.

       -pn    Display  progress  of  translation in the form of a
              line number/file name display.  This  is  refreshed
              every n lines, 25 by default.

       -c rcfile
              Read   local  configuration  commands  from  rcfile
              instead of p2crc or .p2crc.  A  dash  (`-c  -')  in
              place  of rcfile causes no local configuration file
              to be used.

       -v     ("Vanilla.")  Do not read from the system  configu­
              ration  file /usr/lib/p2c/p2crc.  Since some of the
              parameters in this file are  required,  your  local
              configuration  file  must  include those parameters
              instead.  This also suppresses the  file  named  by
              the P2CRC environment variable.

       -H homedir
              Use homedir instead of /usr/lib/p2c as the p2c home
              directory.  The system p2crc file will be  searched
              for in this directory.

       -Ipattern
              Add  pattern to the ImportDir search list of places
              to find modules which are  imported.   The  pattern
              should  include  a %s to represent the module name,
              and should evaluate to a potential  file  name  for
              that  module's source code.  For example, ../%s.pas
              looks for modulename.pas in the parent of the  cur­
              rent directory.

       -i     This  special  option (which must be the only argu­
              ment on the command line if used) simply copies the
              system configuration file /usr/lib/p2c/p2crc to the
              standard output in its entirety.  (It may  be  used
              with  -H,  but -i is most useful precisely when you
              don't know the location of the home directory.)

       -q     Quiet mode.  Suppresses output of  status  messages
              during translation.

       -En    Abort  translation after n errors.  If n is omitted
              it defaults to zero, which means  unlimited  errors
              are  allowed.   Use  -E1 to make p2c halt after the
              first error.

       -e     Echo the Pascal source into the output  file,  sur­
              rounded  by #ifdefs.  This is the same as the Copy­
              Source parameter in the p2crc file.

              ride for the AnsiC parameter in the p2crc file.

       -L language
              Select  input  language name, such as VAX or TURBO.
              This is a  convenient  override  for  the  Language
              parameter.

       -V     Verbose mode.  This causes p2c to generate an addi­
              tional ".log" file  with  further  details  of  the
              translation,  such  as a list of warnings and notes
              including those which are suppressed in the regular
              output.

       -comp  Compiler  mode.  This switch tells p2c to use vari­
              ous configuration defaults that are  more  suitable
              for use as a Pascal compiler rather than a transla­
              tor.  It is the same as  specifying  the  following
              options in your p2crc file:

                   ElimDeadCode 0
                   AnalyzeFlow 0
                   MaxLineBreakTies 0
                   FoldConstants 1
                   FoldStrConstants 1
                   OffsetForLoops 0
                   StaticLinks 1
                   BitwiseMod 0
                   BitwiseDiv 0
                   AssumeBits 0
                   AssumeSigns 0
                   FormatStrings 1
                   StructFiles 1
                   FullStrWrite 1

              The  p2cc script specifies this option when it runs
              p2c to compile a Pascal program.

       -local Local settings.  This switch uses various  configu­
              ration  defaults  that  are appropriate if the code
              generated by p2c is going to be compiled and run on
              the same machine that ran p2c itself.

       -check Enable  all  error  checking.  Normally, some error
              checks are off by default, as described in the com­
              ments in the system p2crc file.

       -M0    Disable  memory  conservation.   This  prevents p2c
              from freeing various data structures  after  trans­
              lating each function, in case this new conservation
              feature causes unforseen problems.

       -R     Regression testing mode.  Formats notes and warning
              messages  in  a  way  that  makes  it easier to run


       P2c also understands a few  debugging  options  which  may
       occasionally  be  useful  when  tracking  down translation
       problems.  The -dn option sets the "debug level" to  n,  a
       small integer which is normally zero.  Debugging output is
       written into the regular output  file  along  with  the  C
       code;  the  higher  your  n, the more "wallpaper" you get.
       Also, -t prints  debugging  information  at  every  Pascal
       token,  -Bn  enables  line-breaker  debugging, -Cn enables
       comment placement debugging, and -Fn enables flow-analysis
       debugging.


CHOICE OF SOURCE LANGUAGE

       The  Language  configuration  parameter or -L command-line
       option tells p2c which Pascal dialect  to  expect  in  the
       input  file.   Any  language features which do not overlap
       between dialects are supported all of the time.  The  Lan­
       guage  parameter  is  consulted  when a syntax or usage is
       detected that has  different  meanings  in  two  different
       dialects, and also to determine default values for various
       other translation parameters as described below.

       The following language words are supported by p2c.   Names
       are case-insensitive.

       HP      HP  Pascal.   This  is  the default language.  All
               features of HP Standard Pascal, the  Pascal  Work­
               station  version, are supported except as noted in
               BUGS  below.   Some  features  of   MODCAL,   HP's
               extended  Pascal,  are  also supported.  This is a
               superset of ISO standard Pascal, including confor­
               mant arrays and procedural parameters.

       HP-UX   HP Pascal, HP-UX version.  Almost identical to the
               "HP" dialect.

       Turbo   Turbo Pascal 5.0 for the IBM  PC.   Few  conflicts
               with  HP  Pascal, so the Language parameter is not
               often needed for Turbo.  (Most important  is  that
               the  Turbo and HP dialects use 16 and 32 bit inte­
               gers, respectively.)

       UCSD    UCSD Pascal.  Similar to Turbo in many ways.

       MPW     Macintosh  Programmer's   Workshop   Pascal   2.0.
               Should  also  do  a pretty good job for Lightspeed
               Pascal.  Object Pascal features are not supported,
               nor  is the fact that char variables are sometimes
               stored in 16 bits.

       VAX     VAX/VMS Pascal version 3.5.  Most but not all lan­
               guage  features  supported.  This has not yet been
               tested on large programs.

               mented.

       Berk    Berkeley Pascal with Sun extensions.

       TIP     Texas Instruments Pascal.

       Apollo  Apollo Domain Pascal.

       Modula  Modula-2.   Based  on  Wirth's Programming in Mod­
               ula-2, 3rd edition.  Proper setting  of  the  Lan­
               guage parameter is not optional.  Translation will
               be incomplete in most cases, but  should  be  good
               enough  to work with.  Structure of local sub-mod­
               ules is essentially  ignored;  like-named  identi­
               fiers may be confused.  Type WORD is translated as
               an integer, but type ADDRESS is translated as char
               * or void *; this may cause inconsistencies in the
               output code.

               Modula-2 modules have two parts in separate files.
               Suppose these are called foo.def (definition part)
               and foo.mod (implementation part) for module  foo.
               Then a pattern like %s.def must be included in the
               ImportDir list, and LibraryFile must be changed to
               refer  to  system.m2  instead  of  system.imp.  To
               translate the definition part, give the command

                    p2c foo.def

               to translate the definition part into files  foo.h
               and  foo.c; the latter will usually be empty.  The
               command

                    p2c -s foo.def foo.mod

               will translate the implementation part  into  file
               foo.c.

       Even if all language features are supported for a dialect,
       some predefined functions may be omitted.  In these cases,
       the function call will be translated literally into C with
       a warning.  Some hand modification may be required.


CONFIGURATION PARAMETERS

       P2c is highly configurable.  The defaults are suitable for
       most  applications,  but customizing these parameters will
       help you get the best  possible  translation.   Since  the
       output of p2c is intended to be used as human-maintainable
       source code, there are many parameters for describing  the
       coding  style  and  conventions  you  prefer.  Others give
       hints about your program that help p2c  to  generate  more
       correct, efficient, or readable code.

       line.  The system configuration file, which may be  viewed
       using  the  -i  option to p2c, serves as an example of the
       proper format.  Parameter names are case-insensitive.   If
       a  parameter name occurs exactly once in the system p2crc,
       this indicates that it must have a unique  value  and  the
       last value given to it by the configuration files is used.
       Other parameters are written several times in a row; these
       are  lists to which each configuration line adds an entry.

       Many p2crc options take a numeric value of 0 or 1, roughly
       corresponding  to  "no" or "yes."  Sometimes a blank value
       or the value "def" corresponds to an intermediate  "maybe"
       state.   For  example,  the  stylistic  option ExtraParens
       switches between copious or minimal parentheses in expres­
       sions,  with  the default being a nice compromise intended
       to be best for readers with  an  average  knowledge  of  C
       operator precedences.

       Configuration  options  may also be embedded in the source
       file in the form of Pascal comments:

            {ShortOpt=0} {AvoidName=fred}
            {FuncMacro slope(x,y)=atan2(y,x)*RadDeg}

       disables automatic short-circuiting of and and or  expres­
       sions,  adds "fred" to the list of names to avoid using in
       generated C code, and defines a  special  translation  for
       the  Pascal  program's slope function using the standard C
       atan2 function and a constant RadDeg presumably defined in
       the  program.   Whitespace  is  generally  not  allowed in
       embedded parameters.  The `=' sign is required for  embed­
       ded  parameters,  though  it  is  optional in p2crc files.
       Comments within embedded parameters are delimited by `##'.
       Numeric  parameters  may  replace  `='  with `+' or `-' to
       increase or decrease the parameter; list-based  parameters
       may  use  `-'  to  remove  a  name from a list rather than
       adding it.  Also, the parameter name by itself in  comment
       braces  means  to  restore  the parameter's value that was
       current before the last change:

            {VarFiles=0  ## Pass FILE *'s params by value even if
       VAR}
            some declarations
            {VarFiles    ## Back to original FILE * passing}

       causes  the  parameter  VarFiles  to  have the value 0 for
       those few declarations, without affecting the  parameter's
       value elsewhere in the file.

       If  an embedded parameter appears in an include file or in
       interface text for a module, the effect of the  assignment
       normally  carries  over to any programs that included that
       file.  If the parameter name is preceded by  a  `*',  then

       file that contains it ends:

            {IncludeFrom strings=<p2c/strings.h>}
            {*ExportSymbol=pascal_%s}
            module strings;

       will record the location of the strings  module's  include
       file  for  the rest of the translation, but the assignment
       of ExportSymbol pertains only to the module itself.

       For the complete list of p2crc parameters,  run  p2c  with
       the  -i  option.   Here  are  some  additional comments on
       selected parameters:

       ImportAll      Because Turbo Pascal only allows  one  unit
                      per source file, p2c normally stops reading
                      past the  word  implementation  in  a  file
                      being  scanned  for interface text.  But HP
                      Pascal allows several modules per file  and
                      so  this  would  not  be  safe  to do.  The
                      ImportAll  option  lets  you  override  the
                      default behavior for your Pascal dialect.

       AnsiC          This  parameter  selects which dialect of C
                      to use.  If 1, all conventions  of  ANSI  C
                      such  as  prototypes, void * pointers, etc.
                      are used.  If 0,  only  strict  K&R  (first
                      edition)  C is used.  The default is to use
                      "traditional UNIX C," which  includes  enum
                      and  void  but  not  void  * or prototypes.
                      Once again there  are  a  number  of  other
                      parameters which may be used to control the
                      individual features if just  setting  AnsiC
                      is not enough.

       C++            This  tells p2c to use a number of language
                      extensions present in  C++:   Specifically,
                      it  enables  the  "//" format for comments,
                      use  of  "anonymous  unions"  for   variant
                      records,  use  of  declarations  within the
                      function body, use of  references  for  VAR
                      parameters,  and  use of "new" and "delete"
                      instead of "malloc" and "free".   P2c  will
                      check  for  collisions  with  C++  reserved
                      words unless you  explicitly  set  the  C++
                      option to zero.

       TurboObjects   P2c   recognizes   two  major  dialects  of
                      object-oriented Pascal.  Turbo  Pascal  6.0
                      object types translate fairly directly into
                      C++ classes.  In Apple's Object Pascal, the
                      object  type  has similar syntax but repre­
                      sents a handle (a  double  pointer)  to  an

                      TurboObjects  option  (whose   default   is
                      determined  by  the  Language setting) says
                      whether objects should be direct  or  indi­
                      rect  through pointers.  (P2c uses pointers
                      instead of handles; p2c is most often  used
                      to  make  programs  more  portable, and few
                      systems except the Mac use handles in  this
                      way.)

       UseVExtern     Many  non-UNIX  linkers  prohibit variables
                      from being defined (not declared)  by  more
                      than  one  source  file.   One  module must
                      declare, e.g., "int foo;", and  all  others
                      must declare "extern int foo;".  P2c accom­
                      plishes this by declaring public  variables
                      "vextern"  in  header  files, and arranging
                      for the macro vextern to expand  to  extern
                      or to nothing when appropriate.  If you set
                      UseVExtern=0 p2c will instead declare vari­
                      ables  in  a simpler way that works only on
                      UNIX-style linkers.

       UseAnyptrMacros
                      Certain  C  reserved  words  have  meanings
                      which may vary from one C implementation to
                      another.   P2c  uses  special   capitalized
                      names  for  these  words;  these  names are
                      defined as macros in the file  p2c.h  which
                      all  translated  programs include.  You can
                      set UseAnyptrMacros=0 to disable the use of
                      these  macros.   Note that the functions of
                      many  of  these  macros  can  also  be  had
                      directly  using other parameters; for exam­
                      ple,  UseConsts  allows  you   to   specify
                      whether your target language recognizes the
                      word const in constant  declarations.   The
                      default  is to use the Const macro instead,
                      so that  your  code  will  be  portable  to
                      either kind of implementation.

                      Signed  expands to the reserved word signed
                      if that word is available, otherwise it  is
                      given  a null definition.  Similarly, Const
                      expands to const if that feature is  avail­
                      able.   The words Volatile and Register are
                      also defined in p2c.h,  although  p2c  does
                      not  use  them  at  present.  The word Char
                      expands to char by default, but might  need
                      to  be redefined to signed char or unsigned
                      char in a particular implementation.   This
                      is used for the Pascal character type; low­
                      ercase char is used when the desired  mean­
                      ing is "byte," not "character."

                      default.  This is used in situations  where
                      a  function  or variable is declared static
                      to make it local to the source file; lower­
                      case  static is used for static local vari­
                      ables.  Thus you can redefine Static to  be
                      null  if you want to force private names to
                      be public for purposes of debugging.

                      The word Void expands to void in all cases;
                      it  is  used when declaring a function with
                      no return value.   The  word  Anyptr  is  a
                      typedef  for void * or char * as necessary;
                      it represents a generic pointer.

       UsePPMacros    The p2c.h header also declares  two  macros
                      for  function  prototyping, PP(x) and PV().
                      These macros are used as follows:

                           Void foo  PP( (int x, int y, Char  *z)
                      );
                           Char *bar PV( );

                      If  prototypes  are available, these macros
                      will expand to

                           Void foo  (int x, int y, Char *z);
                           Char *bar (void);

                      but if only old-style declarations are sup­
                      ported, you instead get

                           Void foo  ();
                           Char *bar ();

                      By  default,  p2c uses these macros for all
                      function declarations, but function defini­
                      tions  are  written  in  old-style  C.  The
                      UsePPMacros parameter can be set  to  0  to
                      disable  all use of PP and PV, or it can be
                      set to 1 to use the macros even when defin­
                      ing  a  function.  (This is accomplished by
                      preceding each old-style definition with  a
                      PP-style  declaration.)   If  you know your
                      code will always  be  compiled  on  systems
                      that support prototyping, it is prettier to
                      set Prototypes=1 or simply AnsiC=1  to  get
                      true function prototypes.

       EatNotes       Notes  and  warning messages containing any
                      of these strings  as  sub-strings  are  not
                      emitted.   Each type of message includes an
                      identifier like [145];  you  can  add  this
                      identifier to the EatNotes list to suppress

                      use  a variable name or other identifier to
                      suppress warnings about that variable.  The
                      strings  are  a  space-separated  list, and
                      thus may not contain embedded  spaces.   To
                      suppress  notes  around  a section of code,
                      use,  e.g.,  {EatNotes+[145]}   and   {Eat­
                      Notes-[145]}.   Most  notes  are  generated
                      during parsing, but to suppress those  gen­
                      erated during output the string may need to
                      remain in the list  far  beyond  the  point
                      where  it appears to be generated.  Use the
                      string "1" or "0" to disable or enable  all
                      notes, respectively.

       ExpandIncludes The  default  action  is  to  expand Pascal
                      include files in-line.   This  may  not  be
                      desirable  if  include files are being used
                      to  simulate   modules.    With   ExpandIn­
                      cludes=0,  p2c  attempts to convert include
                      files containing only whole procedures  and
                      global   declarations   into   analogous  C
                      include files.  This may not  always  work,
                      though;  if  you  get error messages, don't
                      use this option.  By combining this  option
                      with  StaticFunctions=0,  then  doing  some
                      fairly minor editing on the result, you can
                      convert  a  pseudo-modular  Pascal  program
                      into a truly modular collection of C source
                      files.

       ElimDeadCode   Some  transformations  that p2c does on the
                      program may result in unreachable or "dead"
                      code.   By  default  p2c removes such code,
                      but  sometimes  it  removes  more  than  it
                      should.   If  you  have "if false" segments
                      which you wish to retain in C, you may have
                      to set ElimDeadCode=0.

       AnalyzeFlow    By  default  p2c  does  some basic dataflow
                      analysis on the program in  an  attempt  to
                      locate  code  that can be simplified due to
                      knowledge about the possible values of cer­
                      tain  variables.   For  example,  a  Pascal
                      rewrite statement must translate to  an  if
                      that  either  calls  fopen  on  a  formerly
                      closed file  variable,  or  freopen  on  an
                      already-open  file.   If  flow analysis can
                      prove that the file was open or closed upon
                      entry  to  the  statement,  a  much cleaner
                      translation is possible.

                      It is possible that flow analysis will make
                      simplifications  that  are  undesirable  or

                      lyzeFlow to 0 to disable this feature.

       SkipIndices    Normally  Pascal  arrays  not based at zero
                      are "shifted" down for  C,  preserving  the
                      total  size  of  the array.  A Pascal array
                      a[2..10] is translated to a  C  array  a[9]
                      with  references  like  "a[i]"  changed  to
                      "a[i-2]" everywhere.  If SkipIndices is set
                      to a value of 2 or higher, this array would
                      instead be translated  to  a[11]  with  the
                      first   two   elements  never  used.   This
                      arrangement may  generate  incorrect  code,
                      though, for tricky source programs.

       FoldConstants  Pascal  non-structured  constants generally
                      translate to #define's in C.  Set this to 1
                      to  have  constants  instantiated  directly
                      into the code.  This may be  turned  on  or
                      off  around specific constant declarations.
                      Set this to 0 to force p2c  to  make  abso­
                      lutely  no assumptions about the constant's
                      value in generated code, so  that  you  can
                      change  the  constant  later  in the C code
                      without invalidating the translation.   The
                      default  is  to allow p2c to take advantage
                      of its knowledge  of  a  constant's  value,
                      such as by generating code that assumes the
                      constant is positive.

       CharConsts     This   governs   whether   single-character
                      string  literals  in  Pascal const declara­
                      tions should be interpreted  as  characters
                      or  strings.   In other words, const a='x';
                      will translate to #define a 'x' if CharCon­
                      sts=1  (the  default), or to #define a x if
                      CharConsts=0.  Note  that  if  p2c  guesses
                      wrong,  the  generated  code  will  not  be
                      wrong, just uglier.  For example, if  a  is
                      written  as  a  character  constant  but it
                      turns out to be used as a string, p2c  will
                      have  to  write  char-to-string  conversion
                      code each time the constant is used.

       PreserveTypes  P2c makes an attempt to retain the original
                      names used for data types.  For example,

                           type foo = integer; bar = integer;

                      establishes  two  synonyms for the standard
                      integer type; p2c does its best to preserve
                      the  particular  synonym  that  was used to
                      declare each integer variable.  Because the
                      Pascal   language  treats  these  types  as

                      the translation where p2c must fall back on
                      the "true" type, int.  PreserveTypes and  a
                      few related options control whether various
                      kinds of type  names  are  preserved.   The
                      default  settings  preserve  all type names
                      except for pointer  types,  which  use  "*"
                      notation   throught   the   program.   This
                      reflects  the  fact  that   Pascal   forces
                      pointer  types  to be named when tradition­
                      ally they are not separately named in C.

       VarStrings     In HP Pascal, a parameter of the form  "var
                      s : string" will match a string variable of
                      any size; a hidden size parameter is passed
                      which  may be accessed by the Pascal strmax
                      function.  You can prevent p2c from  creat­
                      ing  a  hidden  size  parameter  by setting
                      VarStrings=0.   (Note  that  each  function
                      uses  the  value  of  VarStrings  as of the
                      first declaration of the function  that  is
                      parsed,  which  is  often  in the interface
                      section of a module.)

       Prototypes     Control whether ANSI C function  prototypes
                      are used.  Default is according to AnsiC or
                      C++.  This also controls whether to include
                      parameter names or just their types in sit­
                      uations  where  names  are  optional.   The
                      FullPrototyping parameter allows prototypes
                      to be generated for  declarations  but  not
                      for  definitions  (older versions of Light­
                      speed C required this).  If you use a  mix­
                      ture  of  prototypes  and old-style defini­
                      tions, types like short and float  will  be
                      promoted  to  int and double as required by
                      the ANSI standard,  unless  PromoteArgs  is
                      used to override this.  The CastArgs param­
                      eter controls whether type-casts  are  used
                      in  function arguments; by default they are
                      used only if prototypes are not  available.

       StaticLinks    HP Pascal and Turbo Pascal each include the
                      concept of procedure or function  pointers,
                      though  with  somewhat  different syntaxes.
                      P2c  recognizes  both  notational   styles.
                      Another  difference  is that HP's procedure
                      pointers can point  to  nested  procedures,
                      while Turbo's can point only to global pro­
                      cedures.  In HP Pascal a procedure  pointer
                      must  be stored as a struct containing both
                      a pure C function  pointer  and  a  "static
                      link,"  a pointer to the parent procedure's
                      locals.   (The  static  link  is  NULL  for

                      forced by setting StaticLinks=1.  In Turbo,
                      the default (StaticLinks=0) is to use plain
                      C function pointers with no  static  links.
                      A  third option (StaticLinks=2) uses struc­
                      tures with static links,  but  assumes  the
                      links  are always NULL when calling through
                      a pointer (if you need  compatibility  with
                      the  HP format but know your procedures are
                      global).

       SmallSetConst  Pascal sets are translated into one of  two
                      formats,  depending on the size of the set.
                      If all elements have ordinal values in  the
                      range  0..31,  the  set  is translated as a
                      single integer variable  using  bit  opera­
                      tions.   (The SetBits parameter may be used
                      to change the  upper  limit  of  31.)   The
                      SmallSetConst  parameter  controls  whether
                      these small-sets are used, and, if so,  how
                      constant  sets  should be represented in C.
                      For larger sets, an array of long is  used.
                      The  s[0]  element  contains  the number of
                      succeeding array elements which are in use.
                      Set  elements in the range 0..31 are stored
                      in the s[1] array element, and so on.  Sets
                      are  normalized  so that s[s[0]] is nonzero
                      for any nonempty set.   The  standard  run-
                      time  library  includes  all  the necessary
                      procedures for operating on sets.

       ReturnValueName
                      This is one of  many  "naming  conventions"
                      parameters.  Most of these take the form of
                      a printf-like string containing a %s  where
                      the relevant information should go.  In the
                      case of ReturnValueName, the %s refers to a
                      function  name  and  the  resulting  string
                      gives the name of the variable  to  use  to
                      hold  the  function's return value.  Such a
                      variable will be made if  a  function  con­
                      tains   assignments  to  its  return  value
                      buried within  the  body,  so  that  return
                      statements  cannot  conveniently  be  used.
                      Some parameters (ReturnValueName  included)
                      do  not require the %s to be present in the
                      format string; for  example,  the  standard
                      p2crc  file  stores every function's return
                      value in a variable called Result.

       AlternateName  P2c normally translates Pascal names into C
                      names  verbatim,  but  occasionally this is
                      not possible.  A Pascal name  may  be  a  C
                      reserved  word  or  traditional C name like

                      things  that  are hidden from each other by
                      Pascal's scoping rules but must  be  global
                      in  C.   In  these  situations p2c uses the
                      parameter  AlternateName1  to  generate  an
                      alternative   name  for  the  symbol.   The
                      default is to  add  an  underscore  to  the
                      name.   There  is  also  an  AlternateName2
                      parameter for a second alternate name,  and
                      an  AlternateName  parameter  for  the  nth
                      alternate name.  (The value for this param­
                      eter  should include both a %s and a %d, in
                      either order.)  If these latter  parameters
                      are not defined, p2c applies AlternateName1
                      many times over.

       ExportSymbol   Symbols in the interface section for a Pas­
                      cal  module  are formatted according to the
                      value of ExportSymbol, if any.  It  is  not
                      uncommon to use modulename_%s for this sym­
                      bol; the default is %s,  i.e.,  no  special
                      treatment  for  exported  symbols.   If you
                      also define  the  Export_Symbol  parameter,
                      that  format  is  used instead for exported
                      symbols which contain an underscore charac­
                      ter.  If %S (with a capital "S") appears in
                      the format string it stands for the current
                      module name.

       Alias          If  the  value of this parameter contains a
                      %s, it is a format string  applied  to  the
                      names  of  external functions or variables.
                      If the value does  not  contain  a  %s,  it
                      becomes  the name of the next external sym­
                      bol which  is  declared  (after  which  the
                      parameter is cleared).

       Synonym        This  creates  a synonym for another Pascal
                      symbol or keyword.  The format is

                           Synonym old-name = new-name

                      All occurrences of old-name  in  the  input
                      text  are  treated as if they were new-name
                      by the parser.  If new-name is  a  keyword,
                      old-name will be an equivalent keyword.  If
                      new-name is the name of a predefined  func­
                      tion,  old-name will behave in the same way
                      as that function, and so on.   If  new-name
                      is  omitted,  then  occurrences of old-name
                      are entirely ignored  in  the  input  file.
                      Synonyms  allow  you to skip over a keyword
                      in your  dialect  of  Pascal  that  is  not
                      understood by p2c, or to simulate a keyword

                      with  a  similar  one  that p2c recognizes.
                      Note  that  all  predefined  functions  are
                      available  at  all  times;  if  you  have a
                      library routine that  behaves  like,  e.g.,
                      Turbo  Pascal's  getmem  procedure, you can
                      make your routine a synonym for getmem even
                      if you are not translating in Turbo mode.

       NameOf         This  defines  the  name  to use in C for a
                      specific symbol.  It must appear before the
                      symbol  is  declared in the Pascal code; it
                      is usually placed in the local  p2crc  file
                      for the project.  The format is

                           NameOf pascal-name = C-name

                      By  default, Pascal names map directly onto
                      C names with no change (except for the var­
                      ious  kinds  of formatting outlined above).
                      If the pascal-name  is  of  the  form  mod­
                      ule.name or procedure.name then the command
                      applies only to the instance of the  Pascal
                      name  that  is  global  to  that module, or
                      local to  that  procedure.   Otherwise,  it
                      applies to all usages of the name.

       VarMacro       This  is  analogous to NameOf, but specifi­
                      cally for use with Pascal  variables.   The
                      righthand  side  can  be most any C expres­
                      sion; all references to  the  variable  are
                      expanded  into  that  C  expression.  Names
                      used in the C expression are  taken  verba­
                      tim.   There is also a ConstMacro parameter
                      for  translating  constants  as   arbitrary
                      expressions.  Note that the variable on the
                      lefthand side must actually be declared  in
                      the  program  or  in a module that it uses.
                      The declaration for the  variable  will  be
                      omitted  from the generated code unless the
                      Pascal-name appears in the expression:   If
                      you ask to replace i with i+1, the variable
                      i will still be declared but its value will
                      be  shifted  accordingly.   Note  that if i
                      appears on the lefthand side of an  assign­
                      ment,  p2c  will use algebra to "solve" for
                      i.

                      In all cases where  p2c  parses  C  expres­
                      sions,   all  C  operators  are  recognized
                      except  compound  assignments  like   `+='.
                      (Increment   and  decrement  operators  are
                      allowed.)  All variable and function  names
                      are  assumed  to have integer type, even if

                      program.    A  type-specification  operator
                      `::' has been introduced; it has  the  same
                      precedence as `.' or `->' but the righthand
                      side  must  be  a  Pascal  type  identifier
                      (built-in or defined by your program previ­
                      ously to  when  the  macro  definition  was
                      parsed),   or   an  arbitrary  Pascal  type
                      expression in  parentheses.   The  lefthand
                      argument  is  then  considered  to have the
                      specified type.  This may be  necessary  if
                      your  macro is used in situations where the
                      exact type of the expression must be  known
                      (say, as the argument to a writeln).

       FieldMacro     Here  the  lefthand side must have the form
                      record.field, where record  is  the  Pascal
                      type  or  variable  name  for a record, and
                      field is  a  field  in  that  record.   The
                      righthand  side must be a C expression gen­
                      erally  including  the  name  record.   All
                      instances  of that name are replaced by the
                      actual record being "dotted."  For example,

                           FieldMacro        Rect.topLeft       =
                      topLeft(Rect)

                      translates a[i].topLeft into topLeft(a[i]),
                      where a is an array of Rect.

       FuncMacro      The  lefthand side must be any Pascal func­
                      tion or procedure  name  plus  a  parameter
                      list.   The number of parameters must match
                      the number in the function's uses and  dec­
                      laration.    Calls   to  the  function  are
                      replaced by the C expression on the  right­
                      hand side.  For example,

                           FuncMacro    PtInRect(p,r)   =   PtIn­
                      Rect(p,&r)

                      causes the second argument of  PtInRect  to
                      be  passed  by  reference,  even though the
                      declaration says it's not.  If the function
                      in question is actually defined in the pro­
                      gram or module being translated, the  Func­
                      Macro will not affect the definition but it
                      will affect all calls to the function else­
                      where  in  the module.  FuncMacros can also
                      be applied to predefined  or  never-defined
                      functions.

       ReplaceBefore  This  option specifies a string replacement
                      to be done on  every  Pascal  source  line.


                           ReplaceBefore     "{$ifdef"    "{EMBED
                      #ifdef"         ReplaceBefore    "{$endif}"
                      "{EMBED #endif}"

                      These  lines  rewrite Turbo Pascal compile-
                      time conditionals into  comments  beginning
                      with  the  special  word  EMBED.  This word
                      instructs p2c to format  the  rest  of  the
                      comment  without  "/* */" delimiters, i.e.,
                      the  rest  of  the  comment   is   embedded
                      directly in the output C program.  There is
                      also a ReplaceAfter option, which specifies
                      replacements  to  be  done on the output of
                      p2c.

                      Currently, this feature makes only  literal
                      string   replacements,   not  pattern-based
                      matches.  Some users of p2c have  found  it
                      useful   to   feed  their  Pascal  programs
                      through a more powerful editor like sed  or
                      perl  before  giving  them  to  p2c.  Quite
                      often this is all that is necessary to  get
                      an  acceptable  translation  in the face of
                      unrecognized Pascal  dialects  or  language
                      features.

       IncludeFrom    This specifies that a given module's header
                      should be included from a given place.  The
                      second argument may be surrounded by " " or
                      < > as necessary; if the second argument is
                      omitted,  no include directive will be gen­
                      erated for the module.

       ImportFrom     This specifies that a given module's Pascal
                      interface  text  can  be found in the given
                      file.  The named file should be either  the
                      source  file for the module, or a specially
                      prepared file with the implementation  sec­
                      tion  removed  for speed.  If no ImportFrom
                      entry is  found  for  a  module,  the  path
                      defined  by the ImportDir list is searched.
                      Each entry in the path may  contain  a  %s,
                      which  expands  to  the name of the module.
                      The  default  path  looks  for  %s.pas  and
                      %s.text  in the current directory, then for
                      /usr/lib/p2c/%s.imp.   (where  /usr/lib/p2c
                      is the p2c home directory.)

       StructFunction This parameter is a list of functions which
                      follow the p2c semantics for structure-val­
                      ued  functions (functions returning arrays,
                      sets, and strings, and structs in primitive

                      pointer to a return-value area is passed to
                      the  function as a special first parameter.
                      The function  stores  the  result  in  this
                      area,  then  returns a copy of the pointer.
                      (The standard C function strcpy is an exam­
                      ple  of this concept.  Sprintf also behaves
                      this  way  in  some  dialects;  it   always
                      appears  on the StructFunction list regard­
                      less of the type of  implementation.)   The
                      system  configuration  file includes a list
                      of  common  structured  functions  so  that
                      p2c's optimizer will know how to manipulate
                      them.

       StrlapFunction Functions on this list are structured func­
                      tions  as  above,  but  with the ability to
                      work in-place; that is,  the  same  pointer
                      may be passed as both the return value area
                      and a regular parameter.

       Deterministic  Functions on this list have no side effects
                      or  side  dependencies.   An example is the
                      sin function in the standard math  library;
                      two  calls  with  the same parameter values
                      produce  the  same  result,  and  have   no
                      effects  other than returning a value.  P2c
                      can make use of this knowledge  when  opti­
                      mizing  code for efficiency or readability.
                      Functions on this list are also assumed  to
                      be  relatively  fast, so that it is accept­
                      able to duplicate a call to the function.

       LeaveAlone     Functions on this list are not subjected to
                      the  normal built-in translation rules that
                      p2c  would  otherwise  use.   For  example,
                      adding writeln to this list would translate
                      writeln statements blindly into calls to  a
                      C  writeln()  function,  rather  than being
                      translated into  equivalent  printf  calls.
                      The built-in translation is also suppressed
                      if the function has a FuncMacro.

       BufferedFile   P2c normally assumes binary files will  use
                      read/write, not get/put/^ notation.  A file
                      buffer variable will only be created for  a
                      file  if  buffer  notation  is used for it.
                      For  global  file  variables  this  may  be
                      detected  too  late  (a declaration without
                      buffers may  already  have  been  written).
                      Such files can be listed in BufferedFile to
                      force p2c to allocate buffers for them;  do
                      this if you get a warning message that says
                      it is  necessary.   Set  BufferedFile=1  to

                      File allows you to force certain files  not
                      to have buffers.

       StructFiles    If  p2c  still  can't  translate  your file
                      operations correctly, you can  set  Struct­
                      Files=1  to cause Pascal files to translate
                      into structs which include the usual C FILE
                      pointer,  as  well  as file buffer and file
                      name  fields.   While  the  resulting  code
                      doesn't  look  as  much  like native C, the
                      file structs will allow p2c to do a correct
                      translation in many more cases.

       CheckFileEOF   Normally   only  file-open  operations  are
                      checked  for  errors.    Additional   error
                      checking,  such  as  read-past-end-of-file,
                      can be enabled with parameters like  Check­
                      FileEOF.   These  checks  can make the code
                      very ugly!  If I/O checking is  enabled  by
                      the  program  ($iocheck  on$  in HP Pascal;
                      {$I+} in Turbo; this is always the  default
                      state),  these  checks  will generate fatal
                      errors unless enclosed in an HP Pascal try-
                      recover construct.  If I/O checking is dis­
                      abled, these will cause the global variable
                      P_ioresult   to  be  set  zero  or  nonzero
                      according to the outcome.  The default  for
                      most of these options is to check only when
                      I/O checking is enabled.


ISSUES

       Integer size.  P2c normally generates code  to  work  with
       either  16  or  32  bit ints.  If you know your C integers
       will be 16 or 32 bits, set IntSize appropriately.  In par­
       ticular  setting  IntSize=32  will  generate  much cleaner
       code: p2c no longer must carefully cast function arguments
       between  int  and long.  These casts also will be unneces­
       sary  if  ANSI  prototypes  are  available.   To   disable
       int/long  casting  because  you know at least one of these
       cases will hold, set CastLongArgs=0.  (The CastArgs param­
       eter  similarly  controls  other  types  of casts, such as
       between ints and doubles.)  The Integer16  parameter  con­
       trols  whether Pascal integers are interpreted as 16 or 32
       bits, or translated as native  C  integers.   The  default
       value depends on the Language selected.

       Signed/unsigned  chars.   Pascal  characters  are normally
       "weakly" interpreted as unsigned; this  is  controlled  by
       UnsignedChar.  The default is "either," so that C's native
       char type may be used even if its signed-ness is  unknown.
       Code  that  uses characters outside of the range 0-127 may
       need a different setting.  Alternatively, you can use  the
       types  {SIGNED}  char and {UNSIGNED} char in the few cases

       the  SignedComment  and  UnsignedComment parameters.  (The
       type {UNSIGNED} integer is also recognized.)  The  Signed­
       Char  parameter  tells  whether C characters are signed or
       unsigned (default is "unknown").  The HasSignedChar param­
       eter  tells  whether  the phrase "signed char" is legal in
       the output.  If it is not, p2c may have to translate  Pas­
       cal signed bytes into C shorts.

       Special  types.   P2c understands the following predefined
       Pascal type names: integer, signed integers  depending  on
       Integer16;  longint,  signed  32-bit  integers;  unsigned,
       unsigned 32-bit integers; sword, signed  16-bit  integers;
       word,  unsigned  16-bit  integers;  c_int, signed native C
       integers;  c_uint,  unsigned  native  C  integers;  sbyte,
       signed  8-bit  integers;  byte,  unsigned  8-bit integers;
       real, floating-point  numbers  depending  on  DoubleReals;
       single,  single-precision  floats;  longreal,  double, and
       extended, double-precision  floats;  pointer  and  anyptr,
       generic  pointers  (assignment-compatible with any pointer
       type); string,  generic  string  of  length  StringDefault
       (normally   255);  also,  the  usual  Pascal  types  char,
       boolean, and text.  (If your Pascal uses  different  names
       for  these  concepts,  the  Synonym  option  will  come in
       handy.)

       Embedded code.  It is possible to write a  Pascal  comment
       containing C code to be embedded into the output.  See the
       descriptions of EmbedComment and its relatives in the sys­
       tem  p2crc file.  These techniques are helpful if you plan
       to do repeated translations of code that  is  still  being
       maintained  in  Pascal.  See the description of ReplaceBe­
       fore for an example use of embedded code.

       Comments and blank lines.  P2c collects the comments in  a
       procedure  into  a  list.  All comments and statements are
       stamped with serial numbers which  are  used  to  reattach
       comments  to  statements  even  after code has been added,
       removed, or rearranged during translation.  "Orphan"  com­
       ments  attached  to  statements  that  have  been lost are
       attached to nearby statements or emitted at the end of the
       procedure.   Blank lines are treated as a kind of comment,
       so p2c will also reproduce your usage of blank lines.   If
       the  comment mechanism goes awry, you can disable comments
       with EatComments or disable their being attached  to  code
       with SpitComments.

       Indentation.   P2c  has  a  number of parameters to govern
       indentation of code.  The default values produce  the  GNU
       Emacs  standard  indentation  style, although p2c can do a
       better job since it  knows  more  about  the  code  it  is
       indenting.   Indentation  works  by  applying "indentation
       deltas," which are either absolute numbers (which override
       the  previous  indentation),  or  signed  relative numbers

       specifies  no  change in indentation.  All of the indenta­
       tion options are described in the standard p2crc file.

       Line breaking.  P2c uses an algorithm similar to  the  TeX
       typesetter's  paragraph formatter for breaking long state­
       ments into multiple lines.  A  "penalty"  is  assigned  to
       various  undesirable  aspects of all possible line breaks;
       the "badness" of a set of line breaks is approximately the
       sum  of  all the penalties.  Chief among these are serious
       penalties for overrunning the desired maximum line  length
       (default  78 columns), an infinite penalty for overrunning
       the absolute maximum line length (default  90),  and  pro­
       gressively  greater  penalties  for  breaking at operators
       deeply  nested  in  expressions.    Parameters   such   as
       OpBreakPenalty  control  the  relative  weights of various
       choices.  BreakArith and its neighbors control whether the
       operator  at  a  line break should be placed at the end of
       the previous line or at the beginning of the next.  If you
       don't want any oversize lines, define MaxLineWidth=78.

       Unlike  TeX, p2c's line breaker must actually try all pos­
       sible sets of break points.  To avoid  excessive  computa­
       tion, the total penalty contributed at each decision point
       must sum to  a  nonnegative  value;  negative  values  are
       clipped  up  to zero.  This allows p2c to prune away obvi­
       ously undesirable alternatives in advance.   The  MaxLine­
       BreakTries  parameter  (default  5000)  controls  how many
       alternatives to try before giving up and using the best so
       far.

       PASCAL_MAIN.  P2c generates a call to this function at the
       front of the main program.  In the  (unmodified)  run-time
       library  all  this does is save argc and argv away because
       in both HP and Turbo these are accessed  as  global  vari­
       ables.   If  you  do  not wish to use this feature, define
       ArgCName to be argc, ArgVName to  be  argv,  and  MainName
       (normally  "PASCAL_MAIN")  to be blank.  This will work if
       argc and argv are never accessed outside of your main pro­
       gram.


BUGS

       P2c was designed with the idea that clean, readable output
       in most cases is worth more than guaranteed correct output
       in  extreme  cases.  P2c is not a compiler!  However, ide­
       ally the "extreme" cases would include  only  those  which
       never  arise in real life.  Thus if p2c actually generates
       incorrect code I will consider it a bug, but  I  will  not
       apologize for it. :-)  Below are the major remaining cases
       where this is known to occur.

       Certain kinds of conformant  array  parameters  (including
       multi-dimensional  conformant  arrays)  produce  code that
       declares variable-length  arrays  in  C.   Only  a  few  C

       guage extension.  Otherwise some hand  re-coding  will  be
       required.

       HP Pascal try-recover structures are translated into calls
       to TRY and RECOVER macros, which are defined  to  simulate
       the construct using setjmp and longjmp.  If this emulation
       does not work, define the symbol FAKE_TRY to  cause  these
       macros  to  become  "inert."  (In cases where the error is
       detected by code physically within the  body  of  the  try
       statement,  a C goto to the recover section is always gen­
       erated.)  Also, local file variables in scopes  which  are
       destroyed by an escape are not closed.

       Non-local  GOTO's  and  try-recover  statements  are  each
       implemented, but may conflict if both are  used  at  once.
       Non-local  GOTO's  are  fairly careful about closing files
       that go out of scope but may fail to do so in the presence
       of recursion.

       Arrays  containing  files  are  not initialized to NULL as
       other files are.  In some cases, such  as  file  variables
       allocated by NEW, the file is initialized but not automat­
       ically closed by DISPOSE.

       LINK variables allowing  sub-procedures  access  to  their
       parents' variables are occasionally omitted by mistake, if
       the access is too indirect for p2c  to  notice.   If  this
       happens,  you  can  add  an explicit reference to a parent
       variable in the sub-procedure.  A statement  of  the  form
       "a:=a"  will  count  as  a reference but then be optimized
       away by p2c.

       Many aspects of  Modula-2  are  translated  only  superfi­
       cially.  For example, the type-compatibility properties of
       the WORD and ARRAY OF WORD types  are  only  roughly  mod­
       elled, as are the scope rules concerning modules.

       Parts  of  VAX Pascal are still untreated.  In particular,
       the [UNSAFE] attribute and a few others are not fully sup­
       ported, nor are the semantics of the OPEN procedure.

       Turbo  and  VAX  Pascal's  double, quadruple, and extended
       real types all translate to the C  double  type.   Turbo's
       computational type is not supported at all.

       Because  Pascal strings (with length bytes) are translated
       into C strings (with  null  terminators),  certain  Pascal
       string  tricks  will not work in the translated code.  For
       example  the  assignment  s[0]:=chr(x)  is  translated  to
       s[x]=0  on  the assumption that the string is being short­
       ened.  If x is actually greater than the  current  length,
       but  not of a recognizable form like ord(s[0])+n, then the
       generated  code  will  not  work.   In  VAX  Pascal   this

       of a varying-length string.

       Turbo Pascal's automatic clipping of strings is  not  sup­
       ported.   In  Turbo, if a ten character string is assigned
       to a string[8]  variable,  the  last  two  characters  are
       silently removed.  The code produced by p2c generally will
       overrun the target string instead!   The  StringTruncLimit
       parameter  (80  by  default if Language=Turbo) specifies a
       string size which should be  considered  "short";  assign­
       ments  of  potentially-long  strings to short string vari­
       ables will cause a  warning  but  will  not  automatically
       truncate.  The cure is to use copy in the Pascal source to
       truncate the strings explicitly.


FILES

       file.xxx               Pascal source files
       file.c                 resulting C source file
       module.h               resulting C header file
       p2crc                  local configuration file
       .p2crc                 alternate local configuration file
       /usr/lib/p2c/p2crc     system-wide configuration file
       /usr/lib/p2c/system.impdeclarations for  predefined  func­
       tions
       /usr/lib/p2c/system.m2 analogous declarations for Modula-2
       /usr/lib/p2c/*.imp     interface text for standard modules
       /usr/include/p2c/p2c.h header file for translated programs
       /usr/lib/libp2c.a      run-time library


AUTHOR

       Dave Gillespie, daveg@synaptics.com.

       Many thanks to William Bader,  Steven  Levi,  Rick  Koshi,
       Eric Raymond, Magne Haveraaen, Dirk Grunwald, David Barto,
       Paul Fisher, Tom Schneider,  Dick  Heijne,  Guenther  Saw­
       itzki,  and  many others whose suggestions and bug reports
       have helped improve p2c in countless ways.


Man(1) output converted with man2html