mirror of
https://github.com/vishapoberon/compiler.git
synced 2026-04-05 23:22:25 +00:00
comments in symbol files, viewable by showdef browser.
This commit is contained in:
parent
2f1ce08aff
commit
dac6504f12
6 changed files with 348 additions and 97 deletions
|
|
@ -8,6 +8,7 @@ MODULE OPM; (* RC 6.3.89 / 28.6.89, J.Templ 10.7.89 / 22.7.96 *)
|
||||||
|
|
||||||
CONST
|
CONST
|
||||||
OptionChar* = "-";
|
OptionChar* = "-";
|
||||||
|
MaxCommentLen* = 256;
|
||||||
|
|
||||||
(* compiler option flag bits; don't change the encoding *)
|
(* compiler option flag bits; don't change the encoding *)
|
||||||
inxchk* = 0; (* index check on *)
|
inxchk* = 0; (* index check on *)
|
||||||
|
|
@ -76,15 +77,16 @@ MODULE OPM; (* RC 6.3.89 / 28.6.89, J.Templ 10.7.89 / 22.7.96 *)
|
||||||
BFext = ".c"; (* body file extension *)
|
BFext = ".c"; (* body file extension *)
|
||||||
HFext = ".h"; (* header file extension *)
|
HFext = ".h"; (* header file extension *)
|
||||||
SFtag = 0F7X; (* symbol file tag *)
|
SFtag = 0F7X; (* symbol file tag *)
|
||||||
SFver = 083X; (* symbol file version. Increment if symbol file format is changed. *)
|
SFver = 084X; (* symbol file version. Increment if symbol file format is changed. *)
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
TYPE
|
TYPE
|
||||||
FileName = ARRAY 32 OF CHAR;
|
FileName = ARRAY 32 OF CHAR;
|
||||||
|
|
||||||
VAR
|
VAR
|
||||||
|
currentComment: ARRAY MaxCommentLen OF CHAR;
|
||||||
|
hasComment: BOOLEAN;
|
||||||
|
|
||||||
SourceFileName : ARRAY 256 OF CHAR;
|
SourceFileName : ARRAY 256 OF CHAR;
|
||||||
|
|
||||||
GlobalModel, Model*: ARRAY 10 OF CHAR; (* 2: S8/I16/L32, C: S16/I32/L64, V:S8/I32/L64 *)
|
GlobalModel, Model*: ARRAY 10 OF CHAR; (* 2: S8/I16/L32, C: S16/I32/L64, V:S8/I32/L64 *)
|
||||||
|
|
@ -150,6 +152,33 @@ MODULE OPM; (* RC 6.3.89 / 28.6.89, J.Templ 10.7.89 / 22.7.96 *)
|
||||||
LogW(".");
|
LogW(".");
|
||||||
END LogCompiling;
|
END LogCompiling;
|
||||||
|
|
||||||
|
(* for exported comments *)
|
||||||
|
PROCEDURE StoreComment*(text: ARRAY OF CHAR);
|
||||||
|
VAR i: INTEGER;
|
||||||
|
BEGIN
|
||||||
|
i := 0;
|
||||||
|
WHILE (i < MaxCommentLen - 1) & (text[i] # 0X) DO
|
||||||
|
currentComment[i] := text[i]; INC(i)
|
||||||
|
END;
|
||||||
|
currentComment[i] := 0X;
|
||||||
|
hasComment := TRUE;
|
||||||
|
END StoreComment;
|
||||||
|
|
||||||
|
PROCEDURE GetComment*(VAR text: ARRAY OF CHAR);
|
||||||
|
VAR i: INTEGER;
|
||||||
|
BEGIN
|
||||||
|
IF hasComment THEN
|
||||||
|
i := 0;
|
||||||
|
WHILE (i < LEN(text)) & (i < MaxCommentLen) & (currentComment[i] # 0X) DO
|
||||||
|
text[i] := currentComment[i]; INC(i)
|
||||||
|
END;
|
||||||
|
text[i] := 0X;
|
||||||
|
hasComment := FALSE
|
||||||
|
ELSE
|
||||||
|
text[0] := 0X
|
||||||
|
END;
|
||||||
|
END GetComment;
|
||||||
|
|
||||||
|
|
||||||
(* Integer size support *)
|
(* Integer size support *)
|
||||||
|
|
||||||
|
|
@ -830,4 +859,7 @@ BEGIN
|
||||||
MinReal := -MaxReal;
|
MinReal := -MaxReal;
|
||||||
MinLReal := -MaxLReal;
|
MinLReal := -MaxLReal;
|
||||||
FindInstallDir;
|
FindInstallDir;
|
||||||
|
|
||||||
|
hasComment := FALSE;
|
||||||
|
currentComment[0] := 0X;
|
||||||
END OPM.
|
END OPM.
|
||||||
|
|
|
||||||
|
|
@ -190,22 +190,92 @@ MODULE OPS; (* NW, RC 6.3.89 / 18.10.92 *) (* object model 3.6.92 *)
|
||||||
PROCEDURE Get*(VAR sym: SHORTINT);
|
PROCEDURE Get*(VAR sym: SHORTINT);
|
||||||
VAR s: SHORTINT;
|
VAR s: SHORTINT;
|
||||||
|
|
||||||
PROCEDURE Comment; (* do not read after end of file *)
|
PROCEDURE Comment;
|
||||||
BEGIN OPM.Get(ch);
|
VAR
|
||||||
LOOP
|
isExported: BOOLEAN;
|
||||||
LOOP
|
commentText: ARRAY OPM.MaxCommentLen OF CHAR;
|
||||||
WHILE ch = "(" DO OPM.Get(ch);
|
i: INTEGER;
|
||||||
IF ch = "*" THEN Comment END
|
nestLevel: INTEGER;
|
||||||
END ;
|
prevCh, nextCh: CHAR;
|
||||||
IF ch = "*" THEN OPM.Get(ch); EXIT END ;
|
BEGIN
|
||||||
IF ch = OPM.Eot THEN EXIT END ;
|
FOR i := 0 TO LEN(commentText) - 1 DO
|
||||||
OPM.Get(ch)
|
commentText[i] := 0X
|
||||||
END ;
|
END;
|
||||||
IF ch = ")" THEN OPM.Get(ch); EXIT END ;
|
|
||||||
IF ch = OPM.Eot THEN err(5); EXIT END
|
isExported := FALSE;
|
||||||
END
|
i := 0;
|
||||||
|
nestLevel := 1;
|
||||||
|
prevCh := 0X;
|
||||||
|
|
||||||
|
OPM.Get(ch);
|
||||||
|
|
||||||
|
IF ch = "*" THEN
|
||||||
|
isExported := TRUE;
|
||||||
|
OPM.Get(ch);
|
||||||
|
IF ch = ")" THEN
|
||||||
|
(* Empty exported comment (**), handle and return *)
|
||||||
|
commentText[0] := 0X;
|
||||||
|
OPM.StoreComment(commentText);
|
||||||
|
OPM.Get(ch); (* consume character after closing comment *)
|
||||||
|
RETURN
|
||||||
|
END
|
||||||
|
END;
|
||||||
|
|
||||||
|
WHILE (nestLevel > 0) & (ch # OPM.Eot) DO
|
||||||
|
IF (prevCh = "(") & (ch = "*") THEN
|
||||||
|
INC(nestLevel);
|
||||||
|
prevCh := 0X
|
||||||
|
ELSIF (prevCh = "*") & (ch = ")") THEN
|
||||||
|
DEC(nestLevel);
|
||||||
|
IF nestLevel = 0 THEN
|
||||||
|
OPM.Get(ch); (* move past ')' *)
|
||||||
|
ELSE
|
||||||
|
prevCh := 0X
|
||||||
|
END
|
||||||
|
ELSE
|
||||||
|
IF isExported & (nestLevel = 1) & (prevCh # 0X) THEN
|
||||||
|
IF i < OPM.MaxCommentLen - 1 THEN
|
||||||
|
commentText[i] := prevCh; INC(i)
|
||||||
|
END
|
||||||
|
END;
|
||||||
|
|
||||||
|
prevCh := ch
|
||||||
|
END;
|
||||||
|
|
||||||
|
IF nestLevel > 0 THEN OPM.Get(ch) END
|
||||||
|
END;
|
||||||
|
|
||||||
|
IF ch = OPM.Eot THEN
|
||||||
|
err(5)
|
||||||
|
END;
|
||||||
|
(*
|
||||||
|
IF isExported & (nestLevel = 0) & (prevCh # 0X) & (prevCh # "*") & (i < OPM.MaxCommentLen - 2) THEN
|
||||||
|
commentText[i] := prevCh;
|
||||||
|
INC(i)
|
||||||
|
END;
|
||||||
|
*)
|
||||||
|
IF isExported & (nestLevel = 0) & (prevCh # 0X) & (prevCh # "*") THEN
|
||||||
|
IF i < OPM.MaxCommentLen - 1 THEN
|
||||||
|
commentText[i] := prevCh;
|
||||||
|
INC(i)
|
||||||
|
ELSE
|
||||||
|
OPM.LogWStr("Truncating final comment character"); OPM.LogWLn
|
||||||
|
END
|
||||||
|
END;
|
||||||
|
|
||||||
|
|
||||||
|
IF isExported THEN
|
||||||
|
IF i >= OPM.MaxCommentLen THEN
|
||||||
|
OPM.LogWStr("Warning: commentText overflow"); OPM.LogWLn;
|
||||||
|
i := OPM.MaxCommentLen - 1
|
||||||
|
END;
|
||||||
|
commentText[i] := 0X;
|
||||||
|
OPM.StoreComment(commentText)
|
||||||
|
END;
|
||||||
|
|
||||||
END Comment;
|
END Comment;
|
||||||
|
|
||||||
|
|
||||||
BEGIN
|
BEGIN
|
||||||
OPM.errpos := OPM.curpos-1;
|
OPM.errpos := OPM.curpos-1;
|
||||||
WHILE ch <= " " DO (*ignore control characters*)
|
WHILE ch <= " " DO (*ignore control characters*)
|
||||||
|
|
|
||||||
|
|
@ -46,7 +46,8 @@ TYPE
|
||||||
typ*: Struct;
|
typ*: Struct;
|
||||||
conval*: Const;
|
conval*: Const;
|
||||||
adr*, linkadr*: LONGINT;
|
adr*, linkadr*: LONGINT;
|
||||||
x*: INTEGER (* linkadr and x can be freely used by the backend *)
|
x*: INTEGER; (* linkadr and x can be freely used by the backend *)
|
||||||
|
comment*: ConstExt;
|
||||||
END;
|
END;
|
||||||
|
|
||||||
CONST
|
CONST
|
||||||
|
|
@ -178,6 +179,7 @@ CONST
|
||||||
Shdptr* = 27; Shdpro* = 28; Stpro* = 29; Shdtpro* = 30; Sxpro* = 31;
|
Shdptr* = 27; Shdpro* = 28; Stpro* = 29; Shdtpro* = 30; Sxpro* = 31;
|
||||||
Sipro* = 32; Scpro* = 33; Sstruct* = 34; Ssys* = 35; Sptr* = 36;
|
Sipro* = 32; Scpro* = 33; Sstruct* = 34; Ssys* = 35; Sptr* = 36;
|
||||||
Sarr* = 37; Sdarr* = 38; Srec* = 39; Spro* = 40; Slink* = 37;
|
Sarr* = 37; Sdarr* = 38; Srec* = 39; Spro* = 40; Slink* = 37;
|
||||||
|
Scomment* = 41;
|
||||||
|
|
||||||
TYPE
|
TYPE
|
||||||
ImpCtxt = RECORD
|
ImpCtxt = RECORD
|
||||||
|
|
@ -367,7 +369,15 @@ END NewConst;
|
||||||
|
|
||||||
PROCEDURE NewObj*(): Object;
|
PROCEDURE NewObj*(): Object;
|
||||||
VAR obj: Object;
|
VAR obj: Object;
|
||||||
BEGIN NEW(obj); RETURN obj
|
BEGIN
|
||||||
|
NEW(obj);
|
||||||
|
(* lets fully init pointers *)
|
||||||
|
obj^.typ := NIL;
|
||||||
|
obj^.conval := NIL;
|
||||||
|
obj^.comment := NIL;
|
||||||
|
obj^.name := "";
|
||||||
|
|
||||||
|
RETURN obj
|
||||||
END NewObj;
|
END NewObj;
|
||||||
|
|
||||||
PROCEDURE NewStr*(form, comp: SHORTINT): Struct;
|
PROCEDURE NewStr*(form, comp: SHORTINT): Struct;
|
||||||
|
|
@ -468,8 +478,16 @@ BEGIN
|
||||||
END FindField;
|
END FindField;
|
||||||
|
|
||||||
PROCEDURE Insert*(VAR name: OPS.Name; VAR obj: Object);
|
PROCEDURE Insert*(VAR name: OPS.Name; VAR obj: Object);
|
||||||
VAR ob0, ob1: Object; left: BOOLEAN; mnolev: SHORTINT;
|
VAR
|
||||||
BEGIN ob0 := topScope; ob1 := ob0^.right; left := FALSE;
|
ob0, ob1: Object;
|
||||||
|
left: BOOLEAN;
|
||||||
|
mnolev: SHORTINT;
|
||||||
|
commentText: ARRAY OPM.MaxCommentLen OF CHAR;
|
||||||
|
j: INTEGER;
|
||||||
|
BEGIN
|
||||||
|
ob0 := topScope;
|
||||||
|
ob1 := ob0^.right;
|
||||||
|
left := FALSE;
|
||||||
LOOP
|
LOOP
|
||||||
IF ob1 # NIL THEN
|
IF ob1 # NIL THEN
|
||||||
IF name < ob1^.name THEN ob0 := ob1; ob1 := ob0^.left; left := TRUE
|
IF name < ob1^.name THEN ob0 := ob1; ob1 := ob0^.left; left := TRUE
|
||||||
|
|
@ -480,13 +498,24 @@ BEGIN ob0 := topScope; ob1 := ob0^.right; left := FALSE;
|
||||||
IF left THEN ob0^.left := ob1 ELSE ob0^.right := ob1 END;
|
IF left THEN ob0^.left := ob1 ELSE ob0^.right := ob1 END;
|
||||||
ob1^.left := NIL; ob1^.right := NIL; COPY(name, ob1^.name);
|
ob1^.left := NIL; ob1^.right := NIL; COPY(name, ob1^.name);
|
||||||
mnolev := topScope^.mnolev; ob1^.mnolev := mnolev;
|
mnolev := topScope^.mnolev; ob1^.mnolev := mnolev;
|
||||||
|
(* Attach pending comment *)
|
||||||
|
OPM.GetComment(commentText);
|
||||||
|
IF commentText[0] # 0X THEN
|
||||||
|
NEW(ob1^.comment);
|
||||||
|
(*COPY(commentText, ob1^.comment^);*)
|
||||||
|
j := 0;
|
||||||
|
WHILE (j < OPM.MaxCommentLen - 1) & (commentText[j] # 0X) DO
|
||||||
|
ob1^.comment^[j] := commentText[j];
|
||||||
|
INC(j)
|
||||||
|
END;
|
||||||
|
ob1^.comment^[j] := 0X;
|
||||||
|
END;
|
||||||
EXIT
|
EXIT
|
||||||
END
|
END
|
||||||
END;
|
END;
|
||||||
obj := ob1
|
obj := ob1
|
||||||
END Insert;
|
END Insert;
|
||||||
|
|
||||||
|
|
||||||
(*-------------------------- Fingerprinting --------------------------*)
|
(*-------------------------- Fingerprinting --------------------------*)
|
||||||
|
|
||||||
(* Fingerprints prevent structural type equivalence. *)
|
(* Fingerprints prevent structural type equivalence. *)
|
||||||
|
|
@ -791,13 +820,25 @@ PROCEDURE InSign(mno: SHORTINT; VAR res: Struct; VAR par: Object);
|
||||||
VAR last, new: Object; tag: LONGINT;
|
VAR last, new: Object; tag: LONGINT;
|
||||||
BEGIN
|
BEGIN
|
||||||
InStruct(res);
|
InStruct(res);
|
||||||
tag := OPM.SymRInt(); last := NIL;
|
tag := OPM.SymRInt();
|
||||||
|
last := NIL;
|
||||||
WHILE tag # Send DO
|
WHILE tag # Send DO
|
||||||
new := NewObj(); new^.mnolev := -mno;
|
|
||||||
|
(* Add bounds checking *)
|
||||||
|
IF (tag < 0) OR (tag > 100) THEN
|
||||||
|
OPM.LogWStr("ERROR: Invalid tag value in InSign: "); OPM.LogWNum(tag, 0); OPM.LogWLn;
|
||||||
|
OPM.err(155); (* symbol file corrupted *)
|
||||||
|
RETURN
|
||||||
|
END;
|
||||||
|
|
||||||
|
new := NewObj();
|
||||||
|
new^.mnolev := -mno;
|
||||||
IF last = NIL THEN par := new ELSE last^.link := new END;
|
IF last = NIL THEN par := new ELSE last^.link := new END;
|
||||||
IF tag = Svalpar THEN new^.mode := Var ELSE new^.mode := VarPar END;
|
IF tag = Svalpar THEN new^.mode := Var ELSE new^.mode := VarPar END;
|
||||||
InStruct(new^.typ); new^.adr := OPM.SymRInt(); InName(new^.name);
|
InStruct(new^.typ);
|
||||||
last := new; tag := OPM.SymRInt()
|
new^.adr := OPM.SymRInt(); InName(new^.name);
|
||||||
|
last := new;
|
||||||
|
tag := OPM.SymRInt();
|
||||||
END
|
END
|
||||||
END InSign;
|
END InSign;
|
||||||
|
|
||||||
|
|
@ -973,11 +1014,46 @@ BEGIN
|
||||||
END
|
END
|
||||||
END InStruct;
|
END InStruct;
|
||||||
|
|
||||||
|
|
||||||
PROCEDURE InObj(mno: SHORTINT): Object; (* first number in impCtxt.nextTag *)
|
PROCEDURE InObj(mno: SHORTINT): Object; (* first number in impCtxt.nextTag *)
|
||||||
VAR i, s: INTEGER; ch: CHAR; obj, old: Object; typ: Struct;
|
VAR i, s: INTEGER; ch: CHAR; obj, old: Object; typ: Struct;
|
||||||
tag: LONGINT; ext: ConstExt;
|
tag: LONGINT; ext: ConstExt;
|
||||||
|
commentText: OPS.Name;
|
||||||
|
hasComment : BOOLEAN;
|
||||||
|
j: INTEGER;
|
||||||
|
len: LONGINT;
|
||||||
BEGIN
|
BEGIN
|
||||||
tag := impCtxt.nextTag;
|
tag := impCtxt.nextTag;
|
||||||
|
hasComment := FALSE;
|
||||||
|
|
||||||
|
(* checking for comment first, but not processing it yet *)
|
||||||
|
WHILE tag = Scomment DO (* Handle multiple consecutive comments *)
|
||||||
|
len := OPM.SymRInt(); (* read length *)
|
||||||
|
|
||||||
|
(* Ensure length is within bounds *)
|
||||||
|
IF len < 0 THEN len := 0 END;
|
||||||
|
IF len > OPS.MaxStrLen - 1 THEN len := OPS.MaxStrLen - 1 END;
|
||||||
|
|
||||||
|
i := 0;
|
||||||
|
WHILE i < len DO
|
||||||
|
OPM.SymRCh(commentText[i]); INC(i)
|
||||||
|
END;
|
||||||
|
commentText[i] := 0X;
|
||||||
|
hasComment := TRUE; (* Only keep the last comment if there are multiple *)
|
||||||
|
|
||||||
|
tag := OPM.SymRInt(); (* continue stream *)
|
||||||
|
END;
|
||||||
|
|
||||||
|
(* Now tag should be a valid object tag *)
|
||||||
|
impCtxt.nextTag := tag;
|
||||||
|
|
||||||
|
(* Validate tag value *)
|
||||||
|
IF (tag < 0) OR (tag > 50) THEN
|
||||||
|
OPM.LogWStr("ERROR: Invalid tag in InObj: "); OPM.LogWNum(tag, 0); OPM.LogWLn;
|
||||||
|
OPM.err(155); (* Symbol file error *)
|
||||||
|
RETURN NIL
|
||||||
|
END;
|
||||||
|
|
||||||
IF tag = Stype THEN
|
IF tag = Stype THEN
|
||||||
InStruct(typ); obj := typ^.strobj;
|
InStruct(typ); obj := typ^.strobj;
|
||||||
IF ~impCtxt.self THEN obj^.vis := external END (* type name visible now, obj^.fprint already done *)
|
IF ~impCtxt.self THEN obj^.vis := external END (* type name visible now, obj^.fprint already done *)
|
||||||
|
|
@ -986,7 +1062,7 @@ BEGIN
|
||||||
IF tag <= Pointer THEN (* Constant *)
|
IF tag <= Pointer THEN (* Constant *)
|
||||||
obj^.mode := Con; obj^.conval := NewConst(); InConstant(tag, obj^.conval);
|
obj^.mode := Con; obj^.conval := NewConst(); InConstant(tag, obj^.conval);
|
||||||
obj^.typ := InTyp(tag)
|
obj^.typ := InTyp(tag)
|
||||||
ELSIF tag >= Sxpro THEN
|
ELSIF (tag >= Sxpro) & (tag <= Scpro) THEN (* Procedure tags *)
|
||||||
obj^.conval := NewConst();
|
obj^.conval := NewConst();
|
||||||
obj^.conval^.intval := -1;
|
obj^.conval^.intval := -1;
|
||||||
InSign(mno, obj^.typ, obj^.link);
|
InSign(mno, obj^.typ, obj^.link);
|
||||||
|
|
@ -998,16 +1074,33 @@ BEGIN
|
||||||
s := SHORT(OPM.SymRInt()); ext^[0] := CHR(s); i := 1;
|
s := SHORT(OPM.SymRInt()); ext^[0] := CHR(s); i := 1;
|
||||||
WHILE i <= s DO OPM.SymRCh(ext^[i]); INC(i) END
|
WHILE i <= s DO OPM.SymRCh(ext^[i]); INC(i) END
|
||||||
ELSE OPM.LogWStr("unhandled case at InObj, tag = "); OPM.LogWNum(tag, 0); OPM.LogWLn;
|
ELSE OPM.LogWStr("unhandled case at InObj, tag = "); OPM.LogWNum(tag, 0); OPM.LogWLn;
|
||||||
|
OPM.err(155); RETURN NIL
|
||||||
END
|
END
|
||||||
ELSIF tag = Salias THEN
|
ELSIF tag = Salias THEN
|
||||||
obj^.mode := Typ; InStruct(obj^.typ)
|
obj^.mode := Typ; InStruct(obj^.typ)
|
||||||
ELSE
|
ELSIF (tag = Svar) OR (tag = Srvar) THEN
|
||||||
obj^.mode := Var;
|
obj^.mode := Var;
|
||||||
IF tag = Srvar THEN obj^.vis := externalR END;
|
IF tag = Srvar THEN obj^.vis := externalR END;
|
||||||
InStruct(obj^.typ)
|
InStruct(obj^.typ)
|
||||||
|
ELSE
|
||||||
|
OPM.LogWStr("ERROR: Unexpected tag in InObj: "); OPM.LogWNum(tag, 0); OPM.LogWLn;
|
||||||
|
OPM.err(155); (* Symbol file error *)
|
||||||
|
RETURN NIL
|
||||||
END;
|
END;
|
||||||
InName(obj^.name)
|
InName(obj^.name)
|
||||||
END;
|
END;
|
||||||
|
|
||||||
|
(* attaching exported comment after the object was created *)
|
||||||
|
IF hasComment & (obj # NIL) THEN
|
||||||
|
NEW(obj^.comment);
|
||||||
|
j := 0;
|
||||||
|
WHILE (j < OPM.MaxCommentLen - 1) & (j < len) & (commentText[j] # 0X) DO
|
||||||
|
obj^.comment^[j] := commentText[j];
|
||||||
|
INC(j)
|
||||||
|
END;
|
||||||
|
obj^.comment^[j] := 0X;
|
||||||
|
END;
|
||||||
|
|
||||||
FPrintObj(obj);
|
FPrintObj(obj);
|
||||||
IF (obj^.mode = Var) & ((obj^.typ^.strobj = NIL) OR (obj^.typ^.strobj^.name = "")) THEN
|
IF (obj^.mode = Var) & ((obj^.typ^.strobj = NIL) OR (obj^.typ^.strobj^.name = "")) THEN
|
||||||
(* compute a global fingerprint to avoid structural type equivalence for anonymous types *)
|
(* compute a global fingerprint to avoid structural type equivalence for anonymous types *)
|
||||||
|
|
@ -1040,6 +1133,8 @@ BEGIN
|
||||||
RETURN obj
|
RETURN obj
|
||||||
END InObj;
|
END InObj;
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
PROCEDURE Import*(aliasName: OPS.Name; VAR name: OPS.Name; VAR done: BOOLEAN);
|
PROCEDURE Import*(aliasName: OPS.Name; VAR name: OPS.Name; VAR done: BOOLEAN);
|
||||||
VAR obj: Object; mno: SHORTINT; (* done used in Browser *)
|
VAR obj: Object; mno: SHORTINT; (* done used in Browser *)
|
||||||
BEGIN
|
BEGIN
|
||||||
|
|
@ -1226,45 +1321,71 @@ END Import;
|
||||||
END
|
END
|
||||||
END OutConstant;
|
END OutConstant;
|
||||||
|
|
||||||
PROCEDURE OutObj(obj: Object);
|
PROCEDURE OutTruncatedName(text: ARRAY OF CHAR);
|
||||||
VAR i, j: INTEGER; ext: ConstExt;
|
VAR i: INTEGER;
|
||||||
BEGIN
|
BEGIN
|
||||||
IF obj # NIL THEN
|
i := 0;
|
||||||
OutObj(obj^.left);
|
WHILE (i < OPS.MaxStrLen - 1) & (text[i] # 0X) DO
|
||||||
IF obj^.mode IN {Con, Typ, Var, LProc, XProc, CProc, IProc} THEN
|
OPM.SymWCh(text[i]); INC(i)
|
||||||
IF obj^.history = removed THEN FPrintErr(obj, 250)
|
END;
|
||||||
ELSIF obj^.vis # internal THEN
|
OPM.SymWCh(0X)
|
||||||
CASE obj^.history OF
|
END OutTruncatedName;
|
||||||
| inserted: FPrintErr(obj, 253)
|
|
||||||
| same: (* ok *)
|
|
||||||
| pbmodified: FPrintErr(obj, 252)
|
PROCEDURE OutObj(obj: Object);
|
||||||
| pvmodified: FPrintErr(obj, 251)
|
VAR i, j: INTEGER; ext: ConstExt;
|
||||||
ELSE OPM.LogWStr("unhandled case at OutObj, obj^.history = "); OPM.LogWNum(obj^.history, 0); OPM.LogWLn;
|
k, l: INTEGER;
|
||||||
END;
|
BEGIN
|
||||||
CASE obj^.mode OF
|
IF obj # NIL THEN
|
||||||
| Con: OutConstant(obj); OutName(obj^.name)
|
OutObj(obj^.left);
|
||||||
| Typ: IF obj^.typ^.strobj = obj THEN OPM.SymWInt(Stype); OutStr(obj^.typ)
|
IF obj^.mode IN {Con, Typ, Var, LProc, XProc, CProc, IProc} THEN
|
||||||
ELSE OPM.SymWInt(Salias); OutStr(obj^.typ); OutName(obj^.name)
|
(* Write comment BEFORE the object *)
|
||||||
END
|
IF obj^.comment # NIL THEN
|
||||||
| Var: IF obj^.vis = externalR THEN OPM.SymWInt(Srvar) ELSE OPM.SymWInt(Svar) END;
|
OPM.SymWInt(Scomment);
|
||||||
OutStr(obj^.typ); OutName(obj^.name);
|
(* Calculate actual length of comment text *)
|
||||||
IF (obj^.typ^.strobj = NIL) OR (obj^.typ^.strobj^.name = "") THEN
|
k := 0;
|
||||||
(* compute fingerprint to avoid structural type equivalence *)
|
WHILE (k < OPM.MaxCommentLen - 1) & (obj^.comment^[k] # 0X) DO INC(k) END;
|
||||||
OPM.FPrint(expCtxt.reffp, obj^.typ^.ref)
|
OPM.SymWInt(k); (* length prefix *)
|
||||||
END
|
(* Write comment data as individual characters *)
|
||||||
| XProc: OPM.SymWInt(Sxpro); OutSign(obj^.typ, obj^.link); OutName(obj^.name)
|
l := 0;
|
||||||
| IProc: OPM.SymWInt(Sipro); OutSign(obj^.typ, obj^.link); OutName(obj^.name)
|
WHILE l < k DO
|
||||||
| CProc: OPM.SymWInt(Scpro); OutSign(obj^.typ, obj^.link); ext := obj^.conval^.ext;
|
OPM.SymWCh(obj^.comment^[l]); INC(l)
|
||||||
j := ORD(ext^[0]); i := 1; OPM.SymWInt(j);
|
|
||||||
WHILE i <= j DO OPM.SymWCh(ext^[i]); INC(i) END;
|
|
||||||
OutName(obj^.name)
|
|
||||||
ELSE OPM.LogWStr("unhandled case at OutObj, obj.mode = "); OPM.LogWNum(obj.mode, 0); OPM.LogWLn;
|
|
||||||
END
|
|
||||||
END
|
END
|
||||||
END;
|
END;
|
||||||
OutObj(obj^.right)
|
|
||||||
END
|
IF obj^.history = removed THEN FPrintErr(obj, 250)
|
||||||
END OutObj;
|
ELSIF obj^.vis # internal THEN
|
||||||
|
CASE obj^.history OF
|
||||||
|
| inserted: FPrintErr(obj, 253)
|
||||||
|
| same: (* ok *)
|
||||||
|
| pbmodified: FPrintErr(obj, 252)
|
||||||
|
| pvmodified: FPrintErr(obj, 251)
|
||||||
|
ELSE OPM.LogWStr("unhandled case at OutObj, obj^.history = "); OPM.LogWNum(obj^.history, 0); OPM.LogWLn;
|
||||||
|
END;
|
||||||
|
CASE obj^.mode OF
|
||||||
|
| Con: OutConstant(obj); OutName(obj^.name)
|
||||||
|
| Typ: IF obj^.typ^.strobj = obj THEN OPM.SymWInt(Stype); OutStr(obj^.typ)
|
||||||
|
ELSE OPM.SymWInt(Salias); OutStr(obj^.typ); OutName(obj^.name)
|
||||||
|
END
|
||||||
|
| Var: IF obj^.vis = externalR THEN OPM.SymWInt(Srvar) ELSE OPM.SymWInt(Svar) END;
|
||||||
|
OutStr(obj^.typ); OutName(obj^.name);
|
||||||
|
IF (obj^.typ^.strobj = NIL) OR (obj^.typ^.strobj^.name = "") THEN
|
||||||
|
(* compute fingerprint to avoid structural type equivalence *)
|
||||||
|
OPM.FPrint(expCtxt.reffp, obj^.typ^.ref)
|
||||||
|
END
|
||||||
|
| XProc: OPM.SymWInt(Sxpro); OutSign(obj^.typ, obj^.link); OutName(obj^.name)
|
||||||
|
| IProc: OPM.SymWInt(Sipro); OutSign(obj^.typ, obj^.link); OutName(obj^.name)
|
||||||
|
| CProc: OPM.SymWInt(Scpro); OutSign(obj^.typ, obj^.link); ext := obj^.conval^.ext;
|
||||||
|
j := ORD(ext^[0]); i := 1; OPM.SymWInt(j);
|
||||||
|
WHILE i <= j DO OPM.SymWCh(ext^[i]); INC(i) END;
|
||||||
|
OutName(obj^.name)
|
||||||
|
ELSE OPM.LogWStr("unhandled case at OutObj, obj.mode = "); OPM.LogWNum(obj.mode, 0); OPM.LogWLn;
|
||||||
|
END
|
||||||
|
END
|
||||||
|
END;
|
||||||
|
OutObj(obj^.right)
|
||||||
|
END
|
||||||
|
END OutObj;
|
||||||
|
|
||||||
PROCEDURE Export*(VAR ext, new: BOOLEAN);
|
PROCEDURE Export*(VAR ext, new: BOOLEAN);
|
||||||
VAR i: INTEGER; nofmod: SHORTINT; done: BOOLEAN;
|
VAR i: INTEGER; nofmod: SHORTINT; done: BOOLEAN;
|
||||||
|
|
|
||||||
|
|
@ -1,47 +1,47 @@
|
||||||
(* $Id: IntStr.Mod,v 1.4 1999/09/02 13:07:47 acken Exp $ *)
|
(* $Id: IntStr.Mod,v 1.4 1999/09/02 13:07:47 acken Exp $ *)
|
||||||
MODULE oocIntStr;
|
MODULE oocIntStr;
|
||||||
(* IntStr - Integer-number/string conversions.
|
(* IntStr - Integer-number/string conversions.
|
||||||
Copyright (C) 1995 Michael Griebling
|
Copyright (C) 1995 Michael Griebling
|
||||||
|
|
||||||
This module is free software; you can redistribute it and/or modify
|
This module is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU Lesser General Public License as
|
it under the terms of the GNU Lesser General Public License as
|
||||||
published by the Free Software Foundation; either version 2 of the
|
published by the Free Software Foundation; either version 2 of the
|
||||||
License, or (at your option) any later version.
|
License, or (at your option) any later version.
|
||||||
|
|
||||||
This module is distributed in the hope that it will be useful,
|
This module is distributed in the hope that it will be useful,
|
||||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
GNU Lesser General Public License for more details.
|
GNU Lesser General Public License for more details.
|
||||||
|
|
||||||
You should have received a copy of the GNU Lesser General Public
|
You should have received a copy of the GNU Lesser General Public
|
||||||
License along with this program; if not, write to the Free Software
|
License along with this program; if not, write to the Free Software
|
||||||
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||||
*)
|
*)
|
||||||
|
|
||||||
IMPORT
|
IMPORT
|
||||||
Conv := oocConvTypes, IntConv := oocIntConv;
|
Conv := oocConvTypes, IntConv := oocIntConv;
|
||||||
|
|
||||||
TYPE
|
TYPE
|
||||||
ConvResults*= Conv.ConvResults;
|
ConvResults*= Conv.ConvResults;
|
||||||
(* possible values: strAllRight, strOutOfRange, strWrongFormat, strEmpty *)
|
(** possible values: strAllRight, strOutOfRange, strWrongFormat, strEmpty *)
|
||||||
|
|
||||||
CONST
|
CONST
|
||||||
strAllRight*=Conv.strAllRight;
|
strAllRight*=Conv.strAllRight;
|
||||||
(* the string format is correct for the corresponding conversion *)
|
(** the string format is correct for the corresponding conversion *)
|
||||||
strOutOfRange*=Conv.strOutOfRange;
|
strOutOfRange*=Conv.strOutOfRange;
|
||||||
(* the string is well-formed but the value cannot be represented *)
|
(** the string is well-formed but the value cannot be represented *)
|
||||||
strWrongFormat*=Conv.strWrongFormat;
|
strWrongFormat*=Conv.strWrongFormat;
|
||||||
(* the string is in the wrong format for the conversion *)
|
(** the string is in the wrong format for the conversion *)
|
||||||
strEmpty*=Conv.strEmpty;
|
strEmpty*=Conv.strEmpty;
|
||||||
(* the given string is empty *)
|
(** the given string is empty *)
|
||||||
|
|
||||||
|
|
||||||
(* the string form of a signed whole number is
|
(** the string form of a signed whole number is
|
||||||
["+" | "-"] decimal_digit {decimal_digit}
|
["+" | "-"] decimal_digit {decimal_digit}
|
||||||
*)
|
*)
|
||||||
|
|
||||||
PROCEDURE StrToInt*(str: ARRAY OF CHAR; VAR int: LONGINT; VAR res: ConvResults);
|
PROCEDURE StrToInt*(str: ARRAY OF CHAR; VAR int: LONGINT; VAR res: ConvResults);
|
||||||
(* Ignores any leading spaces in `str'. If the subsequent characters in `str'
|
(** Ignores any leading spaces in `str'. If the subsequent characters in `str'
|
||||||
are in the format of a signed whole number, assigns a corresponding value to
|
are in the format of a signed whole number, assigns a corresponding value to
|
||||||
`int'. Assigns a value indicating the format of `str' to `res'. *)
|
`int'. Assigns a value indicating the format of `str' to `res'. *)
|
||||||
BEGIN
|
BEGIN
|
||||||
|
|
@ -53,7 +53,7 @@ END StrToInt;
|
||||||
|
|
||||||
|
|
||||||
PROCEDURE Reverse (VAR str : ARRAY OF CHAR; start, end : INTEGER);
|
PROCEDURE Reverse (VAR str : ARRAY OF CHAR; start, end : INTEGER);
|
||||||
(* Reverses order of characters in the interval [start..end]. *)
|
(** Reverses order of characters in the interval [start..end]. *)
|
||||||
VAR
|
VAR
|
||||||
h : CHAR;
|
h : CHAR;
|
||||||
BEGIN
|
BEGIN
|
||||||
|
|
@ -65,7 +65,7 @@ END Reverse;
|
||||||
|
|
||||||
|
|
||||||
PROCEDURE IntToStr*(int: LONGINT; VAR str: ARRAY OF CHAR);
|
PROCEDURE IntToStr*(int: LONGINT; VAR str: ARRAY OF CHAR);
|
||||||
(* Converts the value of `int' to string form and copies the possibly truncated
|
(** Converts the value of `int' to string form and copies the possibly truncated
|
||||||
result to `str'. *)
|
result to `str'. *)
|
||||||
CONST
|
CONST
|
||||||
maxLength = 11; (* maximum number of digits representing a LONGINT value *)
|
maxLength = 11; (* maximum number of digits representing a LONGINT value *)
|
||||||
|
|
@ -92,9 +92,9 @@ BEGIN
|
||||||
b[e] := 0X;
|
b[e] := 0X;
|
||||||
Reverse(b, s, e-1)
|
Reverse(b, s, e-1)
|
||||||
END;
|
END;
|
||||||
|
|
||||||
COPY(b, str) (* truncate output if necessary *)
|
COPY(b, str) (* truncate output if necessary *)
|
||||||
END IntToStr;
|
END IntToStr;
|
||||||
|
|
||||||
END oocIntStr.
|
END oocIntStr.
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,4 +1,7 @@
|
||||||
MODULE Out; (* DCW Brown. 2016-09-27 *)
|
MODULE Out; (* DCW Brown. 2016-09-27 *)
|
||||||
|
(** Module Out provides a set of basic routines
|
||||||
|
for formatted output of characters, numbers, and strings.
|
||||||
|
It assumes a standard output stream to which the symbols are written. *)
|
||||||
|
|
||||||
IMPORT SYSTEM, Platform, Heap;
|
IMPORT SYSTEM, Platform, Heap;
|
||||||
|
|
||||||
|
|
@ -16,11 +19,11 @@ BEGIN
|
||||||
IF in > 0 THEN error := Platform.Write(Platform.StdOut, SYSTEM.ADR(buf), in) END;
|
IF in > 0 THEN error := Platform.Write(Platform.StdOut, SYSTEM.ADR(buf), in) END;
|
||||||
in := 0;
|
in := 0;
|
||||||
END Flush;
|
END Flush;
|
||||||
|
(** Initializes the output stream. In this library does nothing, safe to never use. *)
|
||||||
PROCEDURE Open*;
|
PROCEDURE Open*;
|
||||||
BEGIN
|
BEGIN
|
||||||
END Open;
|
END Open;
|
||||||
|
(** Writes the character to the end of the output stream. *)
|
||||||
PROCEDURE Char*(ch: CHAR);
|
PROCEDURE Char*(ch: CHAR);
|
||||||
BEGIN
|
BEGIN
|
||||||
IF in >= LEN(buf) THEN Flush END;
|
IF in >= LEN(buf) THEN Flush END;
|
||||||
|
|
@ -32,7 +35,7 @@ PROCEDURE Length(VAR s: ARRAY OF CHAR): LONGINT;
|
||||||
VAR l: LONGINT;
|
VAR l: LONGINT;
|
||||||
BEGIN l := 0; WHILE (l < LEN(s)) & (s[l] # 0X) DO INC(l) END; RETURN l
|
BEGIN l := 0; WHILE (l < LEN(s)) & (s[l] # 0X) DO INC(l) END; RETURN l
|
||||||
END Length;
|
END Length;
|
||||||
|
(** Writes the null-terminated character sequence str to the end of the output stream (without 0X). *)
|
||||||
PROCEDURE String*(str: ARRAY OF CHAR);
|
PROCEDURE String*(str: ARRAY OF CHAR);
|
||||||
VAR l: LONGINT; error: Platform.ErrorCode;
|
VAR l: LONGINT; error: Platform.ErrorCode;
|
||||||
BEGIN
|
BEGIN
|
||||||
|
|
@ -46,7 +49,10 @@ BEGIN
|
||||||
END
|
END
|
||||||
END String;
|
END String;
|
||||||
|
|
||||||
|
(** Writes the integer number x to the end of the output stream.
|
||||||
|
If the textual representation of x requires m characters,
|
||||||
|
x is right adjusted in a field of Max(n, m) characters
|
||||||
|
padded with blanks at the left end. a plus sign is not written. *)
|
||||||
PROCEDURE Int*(x, n: HUGEINT);
|
PROCEDURE Int*(x, n: HUGEINT);
|
||||||
CONST zero = ORD('0');
|
CONST zero = ORD('0');
|
||||||
VAR s: ARRAY 22 OF CHAR; i: INTEGER; negative: BOOLEAN;
|
VAR s: ARRAY 22 OF CHAR; i: INTEGER; negative: BOOLEAN;
|
||||||
|
|
@ -82,7 +88,7 @@ BEGIN
|
||||||
ELSE Char(CHR((x MOD 16) - 10 + ORD('A'))) END
|
ELSE Char(CHR((x MOD 16) - 10 + ORD('A'))) END
|
||||||
END
|
END
|
||||||
END Hex;
|
END Hex;
|
||||||
|
(** Writes an end-of-line symbol to the end of the output stream *)
|
||||||
PROCEDURE Ln*;
|
PROCEDURE Ln*;
|
||||||
BEGIN String(Platform.NL); Flush;
|
BEGIN String(Platform.NL); Flush;
|
||||||
END Ln;
|
END Ln;
|
||||||
|
|
@ -117,14 +123,15 @@ END Ten;
|
||||||
|
|
||||||
PROCEDURE -Entier64(x: LONGREAL): SYSTEM.INT64 "(INT64)(x)";
|
PROCEDURE -Entier64(x: LONGREAL): SYSTEM.INT64 "(INT64)(x)";
|
||||||
|
|
||||||
PROCEDURE RealP(x: LONGREAL; n: INTEGER; long: BOOLEAN);
|
(** RealP(x, n) writes the long real number x to the end of the output stream using an
|
||||||
|
|
||||||
(* RealP(x, n) writes the long real number x to the end of the output stream using an
|
|
||||||
exponential form. If the textual representation of x requires m characters (including a
|
exponential form. If the textual representation of x requires m characters (including a
|
||||||
three-digit signed exponent), x is right adjusted in a field of Max(n, m) characters padded
|
three-digit signed exponent), x is right adjusted in a field of Max(n, m) characters padded
|
||||||
with blanks at the left end. A plus sign of the mantissa is not written.
|
with blanks at the left end. A plus sign of the mantissa is not written.
|
||||||
LONGREAL is 1/sign, 11/exponent, 52/significand *)
|
LONGREAL is 1/sign, 11/exponent, 52/significand *)
|
||||||
|
|
||||||
|
PROCEDURE RealP(x: LONGREAL; n: INTEGER; long: BOOLEAN);
|
||||||
|
|
||||||
|
|
||||||
VAR
|
VAR
|
||||||
e: INTEGER; (* Exponent field *)
|
e: INTEGER; (* Exponent field *)
|
||||||
f: HUGEINT; (* Fraction field *)
|
f: HUGEINT; (* Fraction field *)
|
||||||
|
|
@ -212,11 +219,18 @@ BEGIN
|
||||||
WHILE i < LEN(s) DO Char(s[i]); INC(i) END
|
WHILE i < LEN(s) DO Char(s[i]); INC(i) END
|
||||||
END RealP;
|
END RealP;
|
||||||
|
|
||||||
|
(** Writes the real number x to the end of the output stream using an exponential
|
||||||
|
form. If the textual representation of x requires m characters (including a
|
||||||
|
two-digit signed exponent), x is right adjusted in a field of Max(n, m) characters
|
||||||
|
padded with blanks at the left end. A plus sign of the mantissa is not written.*)
|
||||||
PROCEDURE Real*(x: REAL; n: INTEGER);
|
PROCEDURE Real*(x: REAL; n: INTEGER);
|
||||||
BEGIN RealP(x, n, FALSE);
|
BEGIN RealP(x, n, FALSE);
|
||||||
END Real;
|
END Real;
|
||||||
|
|
||||||
|
(** Writes the long real number x to the end of the output stream using an exponential form.
|
||||||
|
If the textual representation of x requires m characters (including a three-digit
|
||||||
|
signed exponent), x is right adjusted in a field of Max(n, m) characters padded
|
||||||
|
with blanks at the left end. A plus sign of the mantissa is not written. *)
|
||||||
PROCEDURE LongReal*(x: LONGREAL; n: INTEGER);
|
PROCEDURE LongReal*(x: LONGREAL; n: INTEGER);
|
||||||
BEGIN RealP(x, n, TRUE);
|
BEGIN RealP(x, n, TRUE);
|
||||||
END LongReal;
|
END LongReal;
|
||||||
|
|
@ -224,4 +238,10 @@ END LongReal;
|
||||||
BEGIN
|
BEGIN
|
||||||
IsConsole := Platform.IsConsole(Platform.StdOut);
|
IsConsole := Platform.IsConsole(Platform.StdOut);
|
||||||
in := 0
|
in := 0
|
||||||
|
|
||||||
|
(** This module originally was designed by Martin Reiser
|
||||||
|
for the book "Programming in Oberon".
|
||||||
|
the specification was proposed by H. Moessenbock *)
|
||||||
|
|
||||||
END Out.
|
END Out.
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -63,6 +63,14 @@ MODULE BrowserCmd; (* RC 29.10.93 *) (* object model 4.12.93, command line ver
|
||||||
IF obj # NIL THEN
|
IF obj # NIL THEN
|
||||||
Objects(obj^.left, mode);
|
Objects(obj^.left, mode);
|
||||||
IF obj^.mode IN mode THEN
|
IF obj^.mode IN mode THEN
|
||||||
|
(* Output comment if present *)
|
||||||
|
IF obj^.comment # NIL THEN
|
||||||
|
Indent(1);
|
||||||
|
Ws("(** ");
|
||||||
|
Ws(obj^.comment^);
|
||||||
|
Ws(" *)");
|
||||||
|
Wln
|
||||||
|
END;
|
||||||
CASE obj^.mode OF
|
CASE obj^.mode OF
|
||||||
|OPT.Con: Indent(2); Ws(obj^.name); Ws(" = ");
|
|OPT.Con: Indent(2); Ws(obj^.name); Ws(" = ");
|
||||||
CASE obj^.typ^.form OF
|
CASE obj^.typ^.form OF
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue