home *** CD-ROM | disk | FTP | other *** search
- (*----------------------------------------------------------------------*)
- (* STRUKTO4.PAS *)
- (* Generierung von Programmorganisationsplaenen *)
- (* {$A-} rekursiven Code erzeugen unter CP/M-80 *)
-
- procedure POP_Erstellen;
- var Aktdef, Zwischen : POPDef_Ptr;
- Aktruf : POP_Ptr;
- Basis_Seg, Basis_Ofs,
- Ende_Seg, Ende_Ofs : integer; (*MS-DOS*)
- (* Def_Ende, Basis_POP : integer); CP/M *)
- Ebene : integer;
- POP_Zeile, Strich_Zeile : Text110;
-
- procedure Lese_Def (var Ende_Seg, Ende_Ofs : integer); (*MS-DOS*)
- (* (var Def_Ende : integer); CP/M *)
- var Zwischen : POPDef_Ptr;
- i : integer;
- begin
- repeat
- if Struktur^.Symbol [1] = 'P'
- then begin
- Zwischen := Aktdef;
- new (Aktdef);
- Zwischen^.Next := Aktdef;
- Aktdef^.Name := copy (Struktur^.Bezeichnung, 1,
- length (Struktur^.Bezeichnung) - 1);
- for i := 1 to length (Aktdef^.Name) do
- Aktdef^.Name [i] := upcase (Aktdef^.Name [i]);
- Aktdef^.Waage := nil;
- Aktdef^.Gezeigt := false;
- Aktdef^.Gleich := Zwischen;
- Aktdef^.Next := nil;
- end;
- Zeile := succ (Zeile);
- Struktur := Struktur^.Next;
- if (Zeile >= Zeile_Akt)
- then begin
- Lesen (Zeile_Akt, false);
- Struktur := Anfangs_Pointer;
- end;
- until (Struktur = nil);
- Ende_Seg := seg (Aktdef^); (*MS-DOS*)
- Ende_Ofs := ofs (Aktdef^);
- (* Def_Ende := ord (Aktdef); CP/M *)
- end; (* Lese_Def *)
-
- procedure Verweise_Erstellen (Basis_seg, Basis_Ofs : integer); (*MS-DOS*)
- (* (Basis_POP : integer) CP/M *)
- var Zwischen1 : POP_Ptr;
- Zwischen : POPDef_Ptr;
- Hilf : Text110;
- i, Ort, Ort1 : integer;
- Fehl : set of char;
- Erster, Treffer : boolean;
- begin
- Fehl := ['A'..'Z', 'a'..'z', '0'..'9', '_', '^', '.'];
- repeat
- if (Struktur^.Symbol [1] in ['W', 'A', 'U', 'I', 'C'])
- or (Struktur^.Symbol = '#R')
- then begin
- Zwischen := ptr (Basis_Seg, Basis_Ofs); (*MS-DOS*)
- (* Zwischen := ptr (Basis_POP); CP/M *)
- Zwischen := Zwischen^.Next;
- Hilf := Struktur^.Bezeichnung;
- for i := 1 to length (Hilf) do
- Hilf [i] := upcase (Hilf [i]);
- Ort := pos ('''', Hilf);
- while Ort > 0 do
- begin
- Hilf [Ort] := ' ';
- Ort1 := pos ('''', Hilf);
- if Ort1 > 0
- then delete (Hilf, Ort, Ort1 - Ort + 1);
- Ort := pos ('''', Hilf);
- end;
- Ort1 := pos (':=', Hilf);
- while Zwischen <> nil do
- begin
- Treffer := false;
- while (Zwischen <> nil) and not (Treffer) do
- begin
- Ort := pos (Zwischen^.Name, Hilf);
- Treffer := (Ort > 0) and not
- (Hilf [Ort + length (Zwischen^.Name)] in Fehl);
- if Ort > 1
- then Treffer := Treffer and not (Hilf [Ort - 1] in Fehl);
- if Treffer
- then begin
- if Ort1 > Ort
- then begin
- delete (Hilf, 1, Ort1 - 1);
- Ort1 := 1;
- Treffer := false;
- end;
- end
- else Zwischen := Zwischen^.Next;
- end;
- if Treffer
- then begin
- Zwischen1 := Aktdef^.Waage;
- Treffer := false;
- while (Zwischen1 <> nil) and not (Treffer) do
- begin
- Treffer := (Zwischen = Zwischen1^.Adr);
- Zwischen1 := Zwischen1^.Gleich;
- end;
- if not Treffer
- then begin
- Zwischen1 := Aktruf;
- new (Aktruf);
- Aktruf^.Adr := Zwischen;
- Aktruf^.Gleich := nil;
- if Erster
- then Aktdef^.Waage := Aktruf
- else Zwischen1^.Gleich := Aktruf;
- Erster := false;
- end;
- Zwischen := Zwischen^.Next;
- end;
- end;
- end
- else if Struktur^.Symbol [1] = 'P'
- then begin
- Aktdef := Aktdef^.Next;
- Erster := true;
- end;
- Zeile := succ (Zeile);
- Struktur := Struktur^.Next;
- if (Zeile >= Zeile_Akt)
- then begin
- Lesen (Zeile_Akt, false);
- Struktur := Anfangs_Pointer;
- end;
- until (Struktur = nil);
- end; (* Verweise_Erstellen *)
-
- procedure Schreibe_POP (Start : POP_Ptr);
- var Faktor, i, Ort : integer;
- pAdr : POPDef_Ptr;
- Gesehen : boolean;
- begin
- pAdr := Start^.Adr;
- Faktor := 1 + Ebene * Feldlaenge;
- Ort := length (pAdr^.Name);
- POP_Zeile := POP_Zeile + Waagerecht + pAdr^.Name; (* Name eintragen *)
- POP_Zeile [1] := ' ';
- Gesehen := pAdr^.Gezeigt;
- pAdr^.Gezeigt := true;
- if (pAdr^.Waage <> nil) and not (Gesehen)
- then begin (* 1. Aufruf => Schachtelung erhöhen *)
- if (pAdr^.Waage^.Adr <> nil)
- then begin
- while Ort < Feldlaenge - 2 do
- begin
- POP_Zeile := POP_Zeile + Waagerecht;
- Ort := succ (Ort);
- end;
- if Ort <= Feldlaenge - 2
- then POP_Zeile := POP_Zeile + Obenrechts;
- end;
- writeln (Destination, ' ' : Links, Strich_Zeile);
- writeln (Destination, ' ' : Links, POP_Zeile);
- Strich_Zeile := Strich_Zeile + copy (Blank, 1, Feldlaenge - 1)
- + Senkrecht;
- if (Faktor > 1) and (Start^.Gleich = nil)
- then Strich_Zeile [Faktor - 1] := ' ';
- POP_Zeile := Strich_Zeile;
- if padr^.Waage^.Gleich <> nil
- then POP_Zeile [Faktor - 1 + Feldlaenge] := KreuzLinks
- else POP_Zeile [Faktor - 1 + Feldlaenge] := Untenlinks;
- Ebene := succ (Ebene);
- Schreibe_POP (pAdr^.Waage);
- end
- else begin (* kein 1.Aufruf => Schachtelung bleibt*)
- writeln (Destination, ' ' : Links, Strich_Zeile);
- writeln (Destination, ' ' : Links, POP_Zeile);
- POP_Zeile := Strich_Zeile;
- end;
- if Start^.Gleich <> nil
- then begin (* 2.-n. Aufruf => Schachtelung bleibt *)
- if Start^.Gleich^.Gleich <> nil
- then POP_Zeile [Faktor - 1] := Kreuzlinks
- else POP_Zeile [Faktor - 1] := Untenlinks;
- Schreibe_POP (Start^.Gleich);
- end
- else begin (* kein 2.-n. Aufruf => Schachtelung reduzieren *)
- Ebene := pred (Ebene);
- Faktor := 1 + Ebene * Feldlaenge;
- if Faktor < 1
- then Faktor := 1;
- delete (Strich_Zeile, Faktor, 255);
- POP_Zeile := Strich_Zeile;
- end;
- end; (* Schreibe_POP *)
-
- begin
- Zeile := 1;
- if Zu_Lang
- then begin
- {$I-} reset (STG_Datei); {$I+}
- Datei_Status (Struktur_Name);
- if Datei_Ok
- then Lesen (Zeile_Akt, true);
- end
- else if Anfangs_Pointer = Ende_Pointer
- then Datei_Lesen
- else begin
- {$I-} reset (STG_Datei); {$I+}
- Datei_Status (Struktur_Name);
- end;
- if Datei_Ok and (Struktur_Name <> '')
- then begin
- Init_Phase;
- mark (Aktdef);
- Basis_Seg := seg (Aktdef^); (*MS-DOS*)
- Basis_Ofs := ofs (Aktdef^);
- (* Basis_POP := ord (Aktdef); CP/M *)
- new (Aktdef);
- Struktur := Anfangs_Pointer;
- Lese_Def (Ende_Seg, Ende_Ofs); (* MS-DOS *)
- (* Lese_Def (Def_Ende); CP/M *)
- Aktdef := ptr (Basis_Seg, Basis_Ofs); (*MS-DOS*)
- (* Aktdef := ptr (Basis_POP); CP/M *)
- Ende_Pointer^.Next := Hilfs_Ptr;
- close (STG_Datei);
- {$I-} reset (STG_Datei); {$I+}
- Datei_Status (Struktur_Name);
- Zeile := 1;
- if Datei_Ok and Zu_Lang
- then Lesen (Zeile_Akt, false);
- Struktur := Anfangs_Pointer;
- Verweise_Erstellen (Basis_Seg, Basis_Ofs); (*MS-DOS*)
- (* Verweise_Erstellen (Basis_POP); CP/M *)
- Zwischen := ptr (Ende_Seg, Ende_Ofs); (*MS-DOS*)
- (* Zwischen := ptr (Def_Ende); CP/M *)
- new (Aktruf);
- Aktruf^.Adr := Zwischen;
- Aktruf^.Gleich := nil;
- POP_Zeile := '';
- Strich_Zeile := '';
- Ebene := 0;
- Schreibe_POP (Aktruf);
- writeln (Destination, ' ');
- writeln (Destination, ' ');
- writeln (Destination, ' ');
- Aktdef := ptr (Basis_Seg, Basis_Ofs); (*MS-DOS*)
- (* Aktdef := ptr (Basis_POP); CP/M*)
- release (Aktdef);
- Nachlauf;
- end;
- end; (* POP_Erstellen *)
- (*----------------------------------------------------------------------*)
- (* Ende von STRUKTO4.PAS *)