perm filename PP.2[EAL,HE]1 blob
sn#676485 filedate 1982-09-27 generic text, type C, neo UTF8
COMMENT ⊗ VALID 00006 PAGES
C REC PAGE DESCRIPTION
C00001 00001
C00002 00002 {$NOMAIN Page Printer routines (used by everything) }
C00009 00003 { Externally defined routines from elsewhere: }
C00010 00004 (* Line allocation routines: getLine, relLine *)
C00015 00005 (* Page Printer routines: ppGlitch, ppChar, ppOutNow, ppLine *)
C00019 00006 (* Page Printer routines: pp5, pp10(L), pp20(L), ppInt, ppReal, ppStrng, ppDelChar, ppDtype *)
C00023 ENDMK
C⊗;
{$NOMAIN Page Printer routines (used by everything) }
const
(* Constants from EDIT *)
maxLines = 28; (* smaller on the 11 than on the 10 *)
maxPPLines = 18;
maxBpts = 25;
maxTBpts = 20; (* max could be exceeded by huge case stmnt *)
listinglength = 2000; (* Length of Listingarray *)
(* Random type declarations for OMSI/SAIL compatibility *)
type
byte = 0..255; (* doesn't really belong here, but... *)
ascii = char;
atext = text;
strngp = ↑strng;
linerecp = ↑linerec;
dump = ↑integer;
token = array[1..4] of integer;
cursorp = array[1..4] of integer;
cstring = packed array [1..10] of ascii;
c4str = packed array [1..4] of ascii;
c5str = packed array [1..5] of ascii;
c20str = packed array [1..20] of ascii;
linestr = packed array [1..130] of ascii;
datatypes = (pconstype, varitype, svaltype, vectype, rottype, transtype,
frametype, eventtype, strngtype, labeltype, proctype, arraytype,
reftype, valtype, cmontype, nulltype, undeftype,
dimensiontype, mactype, macargtype, freevartype);
scalar = real;
strng = record
next: strngp;
ch: cstring;
end;
linerec = record
next: linerecp;
start,length: integer
end;
(* Global variables *)
var
(* From ALMAIN *)
b:boolean;
ch:ascii;
ltime: real;
(* From PARSE *)
reswords: array [0..26] of dump;
idents: array [0..26] of dump;
macrostack: array [1..10] of dump;
curmacstack: array [1..10] of dump;
macrodepth: integer;
curchar, maxchar, curline: integer;
curBlock,newDeclarations: dump;
curProc: dump;
pnode: dump;
nodim, distancedim, timedim, angledim,
forcedim, torquedim, veldim, angveldim: dump;
fvstiffdim, mvstiffdim: dump;
filedepth: integer;
curpage: integer;
sysVars,unVars: dump;
errcount: integer;
outerBlock: dump;
curVariable: dump;
curMotion: dump;
endOk,coendOk: integer;
moveLevel: integer;
curErrhandler, curCmon: dump;
endOfLine, backup, expandmacros, flushcomments, dimCheck: boolean;
semiseen, shownline: boolean;
eofError: boolean;
inMove,inCoblock: boolean;
curtoken: token;
file1,file2,file3,file4,file5: atext;
line: linestr;
(* From INTERP *)
curInt, activeInts, readQueue, allPdbs: dump;
curEnv, sysEnv: dump;
clkQueue: dump;
allEvents: dump;
STLevel: integer; (* set by GO *)
etime: integer; (* used by eval *)
curtime: integer; (* Time of day, in ticks *)
stime: integer; (* used for clock queue on 10 *)
msg: dump; (* for AL-ARM interaction *)
inputp: integer; (* current offset into inputLine array above *)
debugLevel: integer;
tSingleThreadMode: boolean;
resched, running, escapeI, singleThreadMode: boolean;
msgp: boolean; (* flag set if any messages pending *)
inputReady: boolean;
inputLine: array [1..20] of ascii;
(* From EDIT *)
lines: array [1..maxLines] of linerecp;
ppLines: array [1..maxPPLines] of linerecp;
marks: array [1..20] of integer;
cursorStack: array [1..15] of cursorp;
bpts: array [1..maxBpts] of dump;
tbpts: array [1..maxTBpts] of dump;
debugPdbs: array [0..10] of dump;
screenheight,dispHeight: integer;
ppBufp,oppBufp,ppOffset,ppSize,nmarks: integer;
lbufp,cursor,ocur,cursorLine,fieldnum,lineNum,findLine,pcLine: integer;
firstDline,topDline,botDline,firstLine,lastLine: integer;
freeLines,oldLines: linerecp;
findStmnt: dump;
nbpts,ntbpts: integer;
eCurInt: dump;
dProg: dump;
smartTerminal: boolean;
setUp,setExpr,setCursor,dontPrint,outFilep,newVarOk,collect: boolean;
eBackup: boolean;
eSingleThreadMode: boolean;
listing: packed array [0..listinglength] of ascii;
lbuf: array [1..160] of ascii;
ppBuf: array [1..100] of ascii;
outFile: atext;
eCurToken: token;
(* Various device & variable pointers *)
speedfactor: dump;
barm: dump;
(* Various constant pointers *)
xhat,yhat,zhat,nilvect: dump;
niltrans: dump;
bpark, ypark, gpark, rpark: dump;
{ Externally defined routines from elsewhere: }
(* From EPUT *)
procedure putReal(s: real); external;
(* From DISP *)
procedure outLine(line,col,start,length: integer); external;
procedure delLine(line,num: integer); external;
procedure beep; external;
(* Line allocation routines: getLine, relLine *)
function getLine(length: integer): linerecp; external;
function getLine;
var f,fo,fp: linerecp; b: boolean;
begin
if length < 10 then length := 10; (* so we don't get too fragmented *)
f := freeLines;
fo := nil;
b := false;
while not b do (* Find a long enough free line *)
if f = nil then b := true
else if f↑.length >= length then b := true
else begin fo := f; f := f↑.next end;
if f <> nil then
begin
if f↑.length < (length + 8) then
begin (* use entire free line *)
if fo = nil then freeLines := f↑.next (* splice out old free line *)
else fo↑.next := f↑.next;
fp := f;
end
else
begin (* split free line in two parts *)
if oldLines = nil then new(fp) (* get a new line *)
else begin fp := oldLines; oldLines := fp↑.next; end;
fp↑.start := f↑.start;
fp↑.length := length;
f↑.start := f↑.start + length;
f↑.length := f↑.length - length;
end;
end
else
begin
(* *** compact screen array??? *** *)
beep; writeln('Gack - no more room in listing array!!!'); break(output); beep;
(* *** do something intelligent here??? *** *)
if oldLines = nil then new(fp) (* get a new line *)
else begin fp := oldLines; oldLines := fp↑.next; end;
fp↑.start := 1; (* this will clobber line editor, but... *)
fp↑.length := length;
beep;
end;
fp↑.next := nil;
getLine := fp;
end;
procedure relLine(l: linerecp); external;
procedure relLine;
var f,fo: linerecp; b: boolean;
begin
if l <> nil then
if l↑.length > 0 then
begin
f := freeLines;
fo := nil;
b := false;
while not b do (* Find a long enough free line *)
if f = nil then b := true
else if f↑.start >= l↑.start then b := true
else begin fo := f; f := f↑.next end;
b := true;
if fo <> nil then
with fo↑ do (* try to merge with last line *)
if (start + length) = l↑.start then
begin length := length + l↑.length; b := false end;
if f <> nil then
if (l↑.start + l↑.length) = f↑.start then (* try to merge with next line *)
if b then
begin (* merge with next line *)
f↑.start := l↑.start;
f↑.length := f↑.length + l↑.length;
b := false
end
else
begin (* can merge last & next now *)
fo↑.length := fo↑.length + f↑.length;
fo↑.next := f↑.next;
f↑.next := oldLines; (* add it to free line queue *)
oldLines := f;
end;
if b then
begin (* need to add to free line list *)
l↑.next := f;
if fo <> nil then fo↑.next := l else freeLines := l;
end
else begin l↑.next := oldLines; oldLines := l end; (* release line pntr *)
end;
end;
(* Page Printer routines: ppGlitch, ppChar, ppOutNow, ppLine *)
procedure ppGlitch; external;
procedure ppGlitch;
var i,j: integer;
procedure clearLine(i: integer); (* Copied from EAUX1A *)
begin
listing[1] := ' ';
outLine(i,1,1,1);
end;
begin
if ppbufp > 0 then (* If anything in buffer *)
begin
ppLines[ppOffset] := getLine(ppBufp); (* get a line to store chars in *)
with ppLines[ppOffset]↑ do
begin
for i := 1 to ppBufp do listing[start+i-1] := ppBuf[i]; (* copy line *)
for i := ppBufp to length-1 do listing[start+i] := chr(0);
outLine(dispHeight+ppOffset+1,oppBufp+1,start+oPPbufp,ppBufp-oppBufp);
end
end
else
begin
ppLines[ppOffset] := nil;
clearLine(dispHeight+ppOffset+1);
end;
PPbufp := 0;
oPPbufp := 0;
if ppOffset >= ppSize then
begin (* need to glitch page printer *)
relLine(ppLines[1]);
for i := 2 to ppSize do ppLines[i-1] := ppLines[i];
ppLines[ppSize] := nil;
if smartTerminal then delLine(dispHeight+2,1)
else
begin
for i := 1 to ppSize-1 do
if ppLines[i] <> nil then
with ppLines[i]↑ do
outLine(dispHeight+i+1,1,start,length) (* re-draw top lines *)
else clearLine(dispHeight+i+1);
clearLine(dispHeight+ppSize+1);
end;
end
else ppOffset := ppOffset + 1; (* just move to next line *)
end;
procedure ppChar(ch: ascii); external;
procedure ppChar;
begin
if ch = chr(15B) then ppGlitch (* scroll up page printer *)
else if ch <> chr(12B) then (* flush linefeeds *)
begin (* add character to pp buffer *)
if ppBufp >= 80 then ppGlitch;
ppBufp := ppBufp + 1;
ppBuf[ppBufp] := ch;
end;
end;
procedure ppOutNow; external;
procedure ppOutNow;
var i: integer;
begin
for i := oppBufp+1 to ppBufp do listing[i-oppBufp] := ppBuf[i];
outLine(dispHeight+ppOffset+1,oppBufp+1,1,ppBufp-oppBufp);
oppBufp := ppBufp;
end;
procedure ppLine; external; (* Does the same as ppGlitch *)
procedure ppLine;
begin
ppChar(chr(15B)); (* cr *)
end;
(* Page Printer routines: pp5, pp10(L), pp20(L), ppInt, ppReal, ppStrng, ppDelChar, ppDtype *)
procedure pp5(ch: c5str; length: integer); external;
procedure pp5;
var i: integer;
begin
for i := 1 to length do ppChar(ch[i]);
end;
procedure pp10(ch: cstring; length: integer); external;
procedure pp10;
var i: integer;
begin
for i := 1 to length do ppChar(ch[i]);
end;
procedure pp10L(ch: cstring; length: integer); external;
procedure pp10L;
begin
if ppBufp > 0 then ppLine;
pp10(ch,length);
end;
procedure pp20(ch: c20str; length: integer); external;
procedure pp20;
var i: integer;
begin
for i := 1 to length do ppChar(ch[i]);
end;
procedure pp20L(ch: c20str; length: integer); external;
procedure pp20L;
begin
if ppBufp > 0 then ppLine;
pp20(ch,length);
end;
procedure ppInt(i: integer); external;
procedure ppInt;
var j,k: integer; n: array [1..9] of integer;
begin
for j := 1 to 9 do (* get individual digits *)
begin n[j] := i mod 10; i := i div 10 end;
j := 9;
while (j > 1) and (n[j] = 0) do j := j - 1; (* ignore leading zeros *)
for k := j downto 1 do ppChar(chr(ord('0')+n[k])); (* print it *)
end;
procedure ppReal(r: real); external;
procedure ppReal;
var i,j: integer;
begin
j := lbufp;
putReal(r);
ppChar(' ');
for i := j+1 to lbufp do ppChar(lbuf[i]); (* print it *)
lbufp := j; (* restore old line buf pntr *)
end;
procedure ppStrng(length: integer; s: strngp); external;
procedure ppStrng;
var i,j: integer;
begin
j := 1;
for i := 1 to length do
begin
ppChar(s↑.ch[j]);
if j = 10 then begin j := 1; s := s↑.next; end
else j := j + 1;
end;
end;
procedure ppDelChar; external; (* for use by INTERP *)
procedure ppDelChar;
begin
if ppBufp > 0 then
begin
ppBuf[ppBufp] := ' ';
listing[1] := ' ';
outLine(dispHeight+ppOffset+1,ppBufp,1,1);
ppBufp := ppBufp - 1;
oppBufp := ppBufp;
end;
end;
procedure ppDtype(d: datatypes); external;
procedure ppDtype;
begin
case d of
svaltype: pp10('scalar ',6);
vectype: pp10('vector ',6);
rottype: pp5('rot ',3);
transtype: pp5('trans',5);
frametype: pp5('frame',5);
eventtype: pp5('event',5);
strngtype: pp10('string ',6);
otherwise {do nothing - should not happen};
end;
end;