home *** CD-ROM | disk | FTP | other *** search
/ Programmer 7500 / MAX_PROGRAMMERS.iso / INFO / TURBOPAS / XREFPAS4.ZIP / XREFPAS.PAS < prev   
Encoding:
Pascal/Delphi Source File  |  1985-11-23  |  9.0 KB  |  303 lines

  1. program XREFPAS;
  2.  
  3. {-----------------------------------------------------------------------
  4.  
  5.  *** TURBO PASCAL (tm) PROGRAM LISTER AND CROSS REFERENCE GENERATOR ***
  6.                          Version 4.00, 11/13/85
  7.                         Author: Glen F. Marshall
  8.  
  9.  Usage: XREFPAS filename [listname]
  10.  
  11.  Where: filename is the input Turbo Pascal program file
  12.  
  13.         listname is the output list file (default is LST:)
  14.  
  15.  Note:  Programs which contain syntax errors may be processed
  16.         incorrectly by this program.
  17.  
  18. -----------------------------------------------------------------------}
  19.  
  20. {$P128,D-,C-,K-,R-,U-}
  21.  
  22. {$I sort.box}
  23. {$I datetime.pas}
  24.  
  25. const
  26.   C1        = 16;            { characters per symbolic name }
  27.   C2        = 12;            { line numbers per printed reference line }
  28.   C3        =  5;            { size of displayed line numbers }
  29.   FF        = #12;           { form-feed character }
  30.   NUL       = #0;            { hex-zero character }
  31.  
  32. type
  33.   State     = (Other,Symbol,Num,Quote,Hex,Com1,Paren,Com2,Com2x);
  34.   IDstr     = string[127];   { Symbolic name string }
  35.   ErrStr    = string[79];    { error message string }
  36.   Word      = record         { sort record }
  37.                 SortKey: string[C1];
  38.                 RefLine: integer;
  39.               end;
  40.  
  41. var
  42.   SortRec:    Word;          { input/output sort record }
  43.   InpFile:    text[4096];    { input file }
  44.   InpName:    IDstr;         { input file name }
  45.   InpStr:     string[255];   { current input string }
  46.   InpPtr:     integer;       { current input character ptr }
  47.   InpChar:    char;          { current input character }
  48.   Scan:       State;         { current input "word" type }
  49.   ID:         IDstr;         { current input symbolic name }
  50.   OutpFile:   text[4096];    { output listing file }
  51.   OutpName:   IDstr;         { output listing file name }
  52.   Title:      string[4];     { listing type: LIST or XREF }
  53.   Date:       DateTimeResult;{ system date }
  54.   Time:       DateTimeResult;{ system time }
  55.   LineNo:     integer;       { current line number }
  56.   PageNo:     integer;       { current page number }
  57.   SortResult: integer;       { sort return-code }
  58.  
  59. procedure Abort(Msg: ErrStr);
  60.   var
  61.     MsDosRegs: record
  62.                  AX, BX, CX, DX, BP, SI, DI, DS, ES, Flags: integer;
  63.                end;
  64.   begin
  65.     with MsDosRegs do begin
  66.       AX := $4000;
  67.       BX := 2;
  68.       CX := ord(Msg[0]);
  69.       DS := seg(Msg[1]);
  70.       DX := ofs(Msg[1]);
  71.       MsDos(MsDosRegs);
  72.     end;
  73.     sound(1000);
  74.     delay(500);
  75.     nosound;
  76.     delay(1500);
  77.     halt;
  78.   end {Abort};
  79.  
  80. procedure Initialize;
  81.   begin
  82.     Date := SysDate;
  83.     Time := SysTime;
  84.     if paramcount < 1 then Abort('Input file name is missing');
  85.     InpName := paramstr(1);
  86.     assign(InpFile,InpName);
  87. {$I-}
  88.     reset(InpFile);
  89. {$I+}
  90.     if ioresult <> 0 then Abort('Input file does not exist');
  91.     if paramcount < 2 then OutpName := 'LST:'
  92.                       else OutpName := paramstr(2);
  93.     assign(OutpFile,OutpName);
  94. {$I-}
  95.     rewrite(OutpFile);
  96. {$I+}
  97.     if ioresult <> 0 then Abort('Output listing file open error');
  98.     if InpName[2] = ':' then delete(InpName,1,2);
  99.     while pos('\',InpName) <> 0 do delete(InpName,1,1);
  100.   end {Initialize};
  101.  
  102. procedure NewPage;
  103.   begin
  104.     PageNo := PageNo+1;
  105.     writeln(OutpFile,FF,Title,': ',InpName,
  106.             Date:10,Time:10,'PAGE ':35,PageNo);
  107.     writeln(OutpFile);
  108.   end {NewPage};
  109.  
  110. function UpStr(var Str): IDstr;
  111.   var
  112.     i : integer;
  113.     s: IDstr absolute Str;
  114.   begin
  115.     UpStr[0] := s[0];
  116.     for i := 1 to length(s) do UpStr[i] := upcase(s[i]);
  117.   end {UpStr};
  118.  
  119. procedure Inp;
  120.   function NewState: State;
  121.     begin
  122.       case upcase(InpChar) of
  123.         ' '         : NewState := Other;
  124.         'A'..'Z','_': NewState := Symbol;
  125.         '0'..'9'    : NewState := Num;
  126.         ''''        : NewState := Quote;
  127.         '$'         : NewState := Hex;
  128.         '{'         : NewState := Com1;
  129.         '('         : NewState := Paren;
  130.         else          NewState := Other;
  131.       end;
  132.     end {NewState};
  133.   procedure writeID;
  134.     function ReservedWord: boolean;
  135.       const
  136.         Wordlist: array[1..44] of string[9] =
  137.           ('ABSOLUTE','AND','ARRAY','BEGIN','CASE','CONST','DIV','DO',
  138.            'DOWNTO','ELSE','END','EXTERNAL','FILE','FOR','FORWARD',
  139.            'FUNCTION','GOTO','IF','IN','INLINE','LABEL','MOD','NIL',
  140.            'NOT','OF','OR','OVERLAY','PACKED','PROCEDURE','PROGRAM',
  141.            'RECORD','REPEAT','SET','SHL','SHR','STRING','THEN','TO',
  142.            'TYPE','UNTIL','VAR','WHILE','WITH','XOR');
  143.       var
  144.         i, j, k: integer;
  145.         UpID: IDstr;
  146.       begin
  147.         UpID := UpStr(ID);
  148.         i := 1;
  149.         j := 44;
  150.         repeat
  151.           k := (i+j) div 2;
  152.           if UpID > Wordlist[k] then i := k+1
  153.                                 else j := k;
  154.         until i = j;
  155.         ReservedWord := (UpID = Wordlist[i]);
  156.       end {ReservedWord};
  157.     begin
  158.       if not ReservedWord then begin
  159.         with SortRec do begin
  160.           SortKey := ID;
  161.           RefLine := LineNo;
  162.         end;
  163.         SortRelease(SortRec);
  164.       end;
  165.       ID[0] := NUL;
  166.     end {writeID};
  167.   begin
  168.     LineNo := 0;
  169.     PageNo := 0;
  170.     Title := 'LIST';
  171.     Scan := Other;
  172.     while not eof(InpFile) do begin
  173.       readln(InpFile,InpStr);
  174.       if (LineNo mod 60) = 0 then NewPage;
  175.       LineNo := LineNo+1;
  176.       writeln(OutpFile,LineNo:C3,' ',InpStr);
  177.       for InpPtr := 1 to length(InpStr) do begin
  178.         InpChar := InpStr[InpPtr];
  179.         case Scan of
  180.           Other:  begin
  181.                     Scan := NewState;
  182.                     if Scan = Symbol then ID := InpChar;
  183.                   end;
  184.           Symbol: begin
  185.                     Scan := NewState;
  186.                     case Scan of
  187.                       Symbol,Num: begin
  188.                                     ID := ID + InpChar;
  189.                                     Scan := Symbol;
  190.                                   end;
  191.                       else        writeID;
  192.                     end;
  193.                   end;
  194.           Num:    if upcase(InpChar) = 'E' then
  195.                     Scan := Other
  196.                   else
  197.                     Scan := NewState;
  198.           Quote:  if InpChar = '''' then Scan := Other;
  199.           Hex:    if not (upcase(InpChar) in['0'..'9','A'..'F']) then
  200.                     Scan := NewState;
  201.           Com1:   if InpChar = '}' then Scan := Other;
  202.           Paren:  if InpChar = '*' then
  203.                     Scan := Com2
  204.                   else begin
  205.                     Scan := NewState;
  206.                     if Scan = Symbol then ID := InpChar;
  207.                   end;
  208.           Com2:   if InpChar = '*' then Scan := Com2x;
  209.           Com2x:  case InpChar of
  210.                     ')': Scan := Other;
  211.                     '*': Scan := Com2x;
  212.                     else Scan := Com2;
  213.                   end;
  214.         end;
  215.       end;
  216.       case Scan of
  217.         Symbol:     begin
  218.                       writeID;
  219.                       Scan := Other;
  220.                     end;
  221.         Com2x:      Scan := Com2;
  222.         Com1, Com2: ;
  223.         else        Scan := Other;
  224.       end;
  225.     end;
  226.     flush(OutpFile);
  227.   end {Inp};
  228.  
  229. function Less;
  230.   var
  231.     SortRec1: Word absolute X;
  232.     SortRec2: Word absolute Y;
  233.     k1, k2: IDstr;
  234.   begin
  235.     k1 := UpStr(SortRec1.SortKey);
  236.     k2 := UpStr(SortRec2.SortKey);
  237.     if k1 = k2 then
  238.       Less := SortRec1.RefLine < SortRec2.RefLine
  239.     else
  240.       Less := k1 < k2;
  241.   end {Less};
  242.  
  243. procedure Outp;
  244.   var
  245.     l: integer;
  246.   begin
  247.     LineNo := 0;
  248.     PageNo := 0;
  249.     Title := 'XREF';
  250.     l := 0;
  251.     ID[0] := NUL;
  252.     while not SortEOS do begin
  253.       SortReturn(SortRec);
  254.       with SortRec do begin
  255.         if length(SortKey) < C1 then begin
  256.           SortKey := SortKey + ' ';
  257.           while length(SortKey) < C1 do SortKey := SortKey + '.';
  258.         end;
  259.         if UpStr(SortKey) <> ID then begin
  260.           if l <> 0 then begin
  261.             writeln(OutpFile);
  262.             LineNo := LineNo+1;
  263.             l := 0;
  264.           end;
  265.           if (LineNo mod 60) = 0 then NewPage;
  266.           write(OutpFile,SortKey,' ');
  267.           ID := UpStr(SortKey);
  268.         end;
  269.         if l = C2 then begin
  270.           writeln(OutpFile);
  271.           LineNo := LineNo+1;
  272.           if (LineNo mod 60) = 0 then NewPage;
  273.           write(OutpFile,' ':C1+1);
  274.           l := 0;
  275.         end ;
  276.         l := l+1;
  277.         write(OutpFile,RefLine:C3);
  278.       end;
  279.     end;
  280.     writeln(OutpFile);
  281.   end {Outp};
  282.  
  283. procedure Terminate;
  284.   begin
  285.     write(OutpFile,FF);
  286.     close(InpFile);
  287.     close(OutpFile);
  288.     case SortResult of
  289.       3:  Abort('Insufficient memory for sort');
  290.       8:  Abort('Internal sort error');
  291.       9:  Abort('Too many records for sort');
  292.       10: Abort('Disk error or disk full during sort');
  293.       11: Abort('Read error during sort');
  294.       12: Abort('File creation error during sort');
  295.     end;
  296.   end {Terminate};
  297.  
  298. begin
  299.   Initialize;
  300.   SortResult := TurboSort(sizeof(SortRec));
  301.   Terminate;
  302. end.
  303.