<> <> <> <> <> <> <<>> DIRECTORY Basics: TYPE USING [BITOR, bytesPerWord, DivMod], BasicTime: TYPE USING [GMT, Now, ToPupTime], CommandUtil: TYPE USING [KeyValue, ListLength, PairList, SetExtension], FS: TYPE USING [ComponentPositions, Error, ExpandName, GetInfo, OpenFileFromStream, StreamOpen], IO: TYPE USING [Close, EndOf, EndOfStream, GetChar, GetIndex, Put, PutChar, PutRope, SetIndex, STREAM, time, UnsafeGetBlock, UnsafePutBlock], OSMiscOps: TYPE USING [GenerateUniqueId], P1: TYPE USING [InstallParseTable, Parse], PGSConDefs: TYPE USING [ FixupBcdHeader, Format, LALRGen, OutModule, PrintGrammar, TabGen, WriteBcdHeader], PGSOps: TYPE USING [PGSPhase], PGSParseData: TYPE, PGSTypes: TYPE, PrincOpsUtils: TYPE USING [Codebase], Rope: TYPE USING [Concat, Equal, Fetch, Length, Replace, ROPE, Substr], TimeStamp: TYPE USING [Stamp]; PGSControl: PROGRAM IMPORTS Basics, BasicTime, CommandUtil, FS, IO, OSMiscOps, P1, PGSConDefs, PGSParseData, PrincOpsUtils, Rope EXPORTS PGSConDefs, PGSOps = { OPEN PGSTypes; eofMark: PUBLIC CARDINAL; totalTokens, numProd, numRules, nextAlias: PUBLIC CARDINAL; warningsLogged: PUBLIC BOOL; flags: PUBLIC ARRAY PGSTypes.Options OF BOOL; symTab: PUBLIC PGSTypes.SymTab; symInfo: PUBLIC PGSTypes.SymInfo; aliases: PUBLIC PGSTypes.Aliases; tokenInfo: PUBLIC PGSTypes.TokenInfo; prodInfo: PUBLIC PGSTypes.ProdInfo; rhsChar: PUBLIC PGSTypes.RhsChar; sLim, tEntries, ntEntries: PUBLIC CARDINAL; bitstrSize: PUBLIC CARDINAL; PGSFail: PUBLIC ERROR = CODE; outStream: IO.STREAM; outeol: PUBLIC PROC[n: INTEGER] = { THROUGH [1..n] DO outStream.PutChar['\n] ENDLOOP}; outchar: PUBLIC PROC[c: CHAR, n: INTEGER] = { THROUGH [1..n] DO outStream.PutChar[c] ENDLOOP}; outstring: PUBLIC PROC[string: Rope.ROPE] = { outStream.PutRope[string]}; outtab: PUBLIC PROC = {outStream.PutChar['\t]}; outnum: PUBLIC PROC[val: INTEGER, cols: NAT, signChar: CHAR_'-] = { i: CARDINAL; power, digits: CARDINAL _ 1; num: CARDINAL _ ABS[val]; sign: CARDINAL = IF val<0 THEN 1 ELSE 0; WHILE (i_power*10)<=num DO power _ i; digits _ digits+1 ENDLOOP; outchar[' , INTEGER[cols]-INTEGER[digits]-INTEGER[sign]]; IF sign#0 THEN outStream.PutChar[signChar]; UNTIL power < 1 DO [i,num] _ Basics.DivMod[num,power]; outStream.PutChar[VAL['0.ORD+i]]; power _ power/10; ENDLOOP }; startTime: BasicTime.GMT; outtime: PUBLIC PROC = {outStream.Put[IO.time[startTime]]}; <> MakeSymTab: PUBLIC PROC[length: CARDINAL] RETURNS[new: SymTab] ~ { new _ NEW[SymTabSeq[length]]; FOR i: CARDINAL IN[0..length) DO new[i] _ '\000 ENDLOOP}; MakeSymInfo: PUBLIC PROC[length: CARDINAL] RETURNS[new: SymInfo] ~ { new _ NEW[SymInfoSeq[length]]; FOR i: CARDINAL IN[0..length) DO new[i] _ nullSymTabEntry ENDLOOP}; MakeAliases: PUBLIC PROC[length: CARDINAL] RETURNS[new: Aliases] ~ { new _ NEW[AliasesSeq[length]]; FOR i: CARDINAL IN[0..length) DO new[i] _ nullAliasEntry ENDLOOP}; MakeTokenInfo: PUBLIC PROC[length: CARDINAL] RETURNS[new: TokenInfo] ~ { new _ NEW[TokenInfoSeq[length]]; FOR i: CARDINAL IN[0..length) DO new[i] _ nullTokenEntry ENDLOOP}; MakeProdInfo: PUBLIC PROC[length: CARDINAL] RETURNS[new: ProdInfo] ~ { new _ NEW[ProdInfoSeq[length]]; FOR i: CARDINAL IN[0..length) DO new[i] _ nullProdEntry ENDLOOP}; MakeCardinals: PROC[length: CARDINAL] RETURNS[new: Cardinals] ~ { new _ NEW[CardinalsSeq[length]]; FOR i: CARDINAL IN[0..length) DO new[i] _ 0 ENDLOOP}; MakeRhsChar: PUBLIC PROC[length: CARDINAL] RETURNS[new: RhsChar] ~ { new _ MakeCardinals[length]}; MakeStateInfo: PUBLIC PROC[length: CARDINAL] RETURNS[new: StateInfo] ~ { new _ NEW[StateInfoSeq[length]]; FOR i: CARDINAL IN[0..length) DO new[i] _ nullStateInfoRec ENDLOOP}; MakeTable: PUBLIC PROC[length: CARDINAL] RETURNS[new: Table] ~ { new _ NEW[TableSeq[length]]; FOR i: CARDINAL IN[0..length) DO new[i] _ nullItemRec ENDLOOP}; MakeBackChain: PUBLIC PROC[length: CARDINAL] RETURNS[new: BackChain] ~ { new _ NEW[BackChainSeq[length]]; FOR i: CARDINAL IN[0..length) DO new[i] _ nullChainRec ENDLOOP}; MakeStack: PUBLIC PROC[length: CARDINAL] RETURNS[new: Stack] ~ { new _ MakeCardinals[length]}; MakeBitsInfo: PUBLIC PROC[length: CARDINAL] RETURNS[new: BitsInfo] ~ { new _ NEW[BitsInfoSeq[length]]; FOR i: CARDINAL IN[0..length) DO new[i] _ nullContextRec ENDLOOP}; MakeBitString: PUBLIC PROC[length, width: CARDINAL] RETURNS[new: BitString] ~ { size: CARDINAL ~ length*width; new _ NEW[BitStringSeq[size] _ [length: length, width: width, seq: ]]; FOR i: CARDINAL IN[0..size) DO new[i] _ 0 ENDLOOP}; MakeAttrVec: PUBLIC PROC[length: CARDINAL] RETURNS[new: AttrVec] ~ { new _ MakeCardinals[length]}; MakeHashTab: PUBLIC PROC[length: CARDINAL] RETURNS[new: HashTab] ~ { new _ NEW[HashTabSeq[length]]; FOR i: CARDINAL IN[0..length) DO new[i] _ nullHashTabRec ENDLOOP}; MakeTab: PUBLIC PROC[length: CARDINAL] RETURNS[new: Tab] ~ { new _ NEW[TabSeq[length]]; FOR i: CARDINAL IN[0..length) DO new[i] _ nullTabRec ENDLOOP}; MakeColumn: PUBLIC PROC[length: CARDINAL] RETURNS[new: Column] ~ { new _ NEW[ColumnSeq[length]]; FOR i: CARDINAL IN[0..length) DO new[i] _ nullColumnRec ENDLOOP}; MakeStateData: PUBLIC PROC[length: CARDINAL] RETURNS[new: StateData] ~ { new _ NEW[StateDataSeq[length]]; FOR i: CARDINAL IN[0..length) DO new[i] _ nullStateDataRec ENDLOOP}; MakeNTDefaults: PUBLIC PROC[length: CARDINAL] RETURNS[new: NTDefaults] ~ { new _ NEW[NTDefaultsSeq[length]]; FOR i: CARDINAL IN[0..length) DO new[i] _ nullNTDefaultRec ENDLOOP}; MakeRenumber: PUBLIC PROC[length: CARDINAL] RETURNS[new: Renumber] ~ { new _ MakeCardinals[length]}; MakeVocabIndex: PUBLIC PROC[length: CARDINAL] RETURNS[new: VocabIndex] ~ { new _ MakeCardinals[length]}; MakeSInfo: PUBLIC PROC[length: CARDINAL] RETURNS[new: SInfo] ~ { new _ NEW[SInfoSeq[length]]; FOR i: CARDINAL IN[0..length) DO new[i] _ nullSInfoRec ENDLOOP}; MakePInfo: PUBLIC PROC[length: CARDINAL] RETURNS[new: PInfo] ~ { new _ NEW[PInfoSeq[length]]; FOR i: CARDINAL IN[0..length) DO new[i] _ nullPInfoRec ENDLOOP}; <<>> ExpandSymTab: PUBLIC PROC[old: SymTab, ext: CARDINAL] RETURNS[new: SymTab] ~ { new _ NEW[SymTabSeq[old.length+ext]]; FOR i: CARDINAL IN [0..old.length) DO new[i] _ old[i] ENDLOOP; FOR i: CARDINAL IN [old.length..new.length) DO new[i] _ '\000 ENDLOOP}; ExpandSymInfo: PUBLIC PROC[old: SymInfo, ext: CARDINAL] RETURNS[new: SymInfo] ~ { new _ NEW[SymInfoSeq[old.length+ext]]; FOR i: CARDINAL IN [0..old.length) DO new[i] _ old[i] ENDLOOP; FOR i: CARDINAL IN [old.length..new.length) DO new[i] _ nullSymTabEntry ENDLOOP}; ExpandAliases: PUBLIC PROC[old: Aliases, ext: CARDINAL] RETURNS[new: Aliases] ~ { new _ NEW[AliasesSeq[old.length+ext]]; FOR i: CARDINAL IN [0..old.length) DO new[i] _ old[i] ENDLOOP; FOR i: CARDINAL IN [old.length..new.length) DO new[i] _ nullAliasEntry ENDLOOP}; ExpandProdInfo: PUBLIC PROC[old: ProdInfo, ext: CARDINAL] RETURNS[new: ProdInfo] ~ { new _ NEW[ProdInfoSeq[old.length+ext]]; FOR i: CARDINAL IN [0..old.length) DO new[i] _ old[i] ENDLOOP; FOR i: CARDINAL IN [old.length..new.length) DO new[i] _ nullProdEntry ENDLOOP}; ExpandCardinals: PROC[old: Cardinals, ext: CARDINAL] RETURNS[new: Cardinals] ~ { new _ NEW[CardinalsSeq[old.length+ext]]; FOR i: CARDINAL IN [0..old.length) DO new[i] _ old[i] ENDLOOP; FOR i: CARDINAL IN [old.length..new.length) DO new[i] _ 0 ENDLOOP}; ExpandRhsChar: PUBLIC PROC[old: RhsChar, ext: CARDINAL] RETURNS[new: RhsChar] ~ { new _ ExpandCardinals[old, ext]}; ExpandStateInfo: PUBLIC PROC[old: StateInfo, ext: CARDINAL] RETURNS[new: StateInfo] ~ { new _ NEW[StateInfoSeq[old.length+ext]]; FOR i: CARDINAL IN [0..old.length) DO new[i] _ old[i] ENDLOOP; FOR i: CARDINAL IN [old.length..new.length) DO new[i] _ nullStateInfoRec ENDLOOP}; ExpandStack: PUBLIC PROC[old: Stack, ext: CARDINAL] RETURNS[new: Stack] ~ { new _ ExpandCardinals[old, ext]}; ExpandBitsInfo: PUBLIC PROC[old: BitsInfo, ext: CARDINAL] RETURNS[new: BitsInfo] ~ { new _ NEW[BitsInfoSeq[old.length+ext]]; FOR i: CARDINAL IN [0..old.length) DO new[i] _ old[i] ENDLOOP; FOR i: CARDINAL IN [old.length..new.length) DO new[i] _ nullContextRec ENDLOOP}; ExpandBitString: PUBLIC PROC[old: BitString, ext: CARDINAL] RETURNS[new: BitString] ~ { size: CARDINAL ~ (old.length+ext)*old.width; new _ NEW[BitStringSeq[size] _ [length: old.length+ext, width: old.width, seq: ]]; FOR i: CARDINAL IN [0..old.size) DO new[i] _ old[i] ENDLOOP; FOR i: CARDINAL IN [old.size..new.size) DO new[i] _ 0 ENDLOOP}; ExpandSInfo: PUBLIC PROC[old: SInfo, ext: CARDINAL] RETURNS[new: SInfo] ~ { new _ NEW[SInfoSeq[old.length+ext]]; FOR i: CARDINAL IN [0..old.length) DO new[i] _ old[i] ENDLOOP; FOR i: CARDINAL IN [old.length..new.length) DO new[i] _ nullSInfoRec ENDLOOP}; ExpandPInfo: PUBLIC PROC[old: PInfo, ext: CARDINAL] RETURNS[new: PInfo] ~ { new _ NEW[PInfoSeq[old.length+ext]]; FOR i: CARDINAL IN [0..old.length) DO new[i] _ old[i] ENDLOOP; FOR i: CARDINAL IN [old.length..new.length) DO new[i] _ nullPInfoRec ENDLOOP}; orCount: PUBLIC CARDINAL _ 0; OrBits: PUBLIC PROC[source: BitString, sourceI: CARDINAL, sink: BitString, sinkI: CARDINAL] = { sourceBase: CARDINAL ~ sourceI*source.width; sinkBase: CARDINAL ~ sinkI*sink.width; IF source.width#sink.width THEN ERROR; FOR i: CARDINAL IN [0..source.width) DO sink[sinkBase+i] _ Basics.BITOR[sink[sinkBase+i], source[sourceBase+i]]; ENDLOOP; orCount _ orCount+1}; <> sourcestr, outstr, errstr: IO.STREAM _ NIL; <> sourceName: PUBLIC Rope.ROPE _ NIL; sourceVersion: PUBLIC TimeStamp.Stamp; objectName: Rope.ROPE _ NIL; objectVersion: PUBLIC TimeStamp.Stamp; defsName: Rope.ROPE _ NIL; gfName: Rope.ROPE _ NIL; CreateTime: PROC [s: IO.STREAM] RETURNS [LONG CARDINAL] = { RETURN[BasicTime.ToPupTime[FS.GetInfo[FS.OpenFileFromStream[s]].created]]}; getstream: PROC [dotstring: Rope.ROPE] RETURNS [IO.STREAM] = { RETURN [FS.StreamOpen[Rope.Concat[rootName, dotstring], $create]]}; seterrstream: PUBLIC PROC = { IF errstr = NIL THEN { outStream _ errstr _ getstream[".errlog"]; outstring["Cedar PGS of "]; outtime[]; outstring[" -- "]; outstring[rootName]; outstring[".errlog"]; outeol[2]; } ELSE outStream _ errstr}; closeerrstream: PROC = {IF errstr # NIL THEN {IO.Close[errstr]; errstr _ NIL}}; setoutstream: PUBLIC PROC[dotstring: Rope.ROPE] = {outStream _ outstr _ getstream[dotstring]}; resetoutstream: PUBLIC PROC = {outStream _ outstr}; closeoutstream: PUBLIC PROC = {IF outstr # NIL THEN {IO.Close[outstr]; outstr _ NIL}}; cleanupstreams: PUBLIC PROC = {NULL}; -- used for checkout openwordstream: PUBLIC PROC[scratch: BOOL] = { outstr _ FS.StreamOpen[objectName, $create]}; closewordstream: PUBLIC PROC = {closeoutstream[]}; bpw: NAT ~ Basics.bytesPerWord; inword: PUBLIC PROC RETURNS[n: CARDINAL] = { -- note: reads from outstr! base: LONG POINTER ~ @n; IF outstr.UnsafeGetBlock[[base: base, count: bpw]]=bpw THEN RETURN[n] ELSE ERROR IO.EndOfStream[outstr] }; outword: PUBLIC PROC [n: CARDINAL] = { base: LONG POINTER ~ @n; outstr.UnsafePutBlock[[base: base, count: bpw]]}; outblock: PUBLIC PROC [address: LONG POINTER, words: CARDINAL, offset: CARDINAL_0] = { outstr.UnsafePutBlock[[base: address, startIndex: offset*bpw, count: words*bpw]]}; inchar: PUBLIC PROC RETURNS [c: CHAR, end: BOOL] = { IF (end _ sourcestr.EndOf[]) THEN c _ '\000 ELSE c _ sourcestr.GetChar[]}; <> Logger: PROC[proc: PROC[log: IO.STREAM]] = { seterrstream[]; proc[outStream]; resetoutstream[]}; <> StreamIndex: TYPE = INT; -- FileStream.FileByteIndex sourceOrigin: StreamIndex; getindex: PUBLIC PROC RETURNS[CARDINAL] = { RETURN[sourcestr.GetIndex[]-sourceOrigin]}; setindex: PUBLIC PROC[index: CARDINAL] = { sourcestr.SetIndex[sourceOrigin+index]}; <> rootName: Rope.ROPE _ NIL; GetRoot: PROC[fileName: Rope.ROPE] RETURNS[Rope.ROPE] ~ { fullFName: Rope.ROPE; cp: FS.ComponentPositions; [fullFName: fullFName, cp: cp] _ FS.ExpandName[name: fileName]; RETURN[fullFName.Substr[cp.base.start, cp.base.length]]}; SetRoot: PROC [s: Rope.ROPE] = {rootName _ GetRoot[s]}; SetFileName: PROC[fileName, default, extension: Rope.ROPE] RETURNS[Rope.ROPE] = { root: Rope.ROPE = IF fileName = NIL THEN default ELSE fileName; RETURN[CommandUtil.SetExtension[root, extension]]}; TestExtension: PROC[fileName, extension: Rope.ROPE] RETURNS[BOOL] = { fullFName, ext: Rope.ROPE; cp: FS.ComponentPositions; [fullFName: fullFName, cp: cp] _ FS.ExpandName[name: fileName]; ext _ fullFName.Substr[cp.ext.start, cp.ext.length]; RETURN[Rope.Equal[ext, extension, FALSE]]}; ReplaceExtension: PROC[fileName, extension: Rope.ROPE] RETURNS[Rope.ROPE] = { fullFName: Rope.ROPE; cp: FS.ComponentPositions; [fullFName: fullFName, cp: cp] _ FS.ExpandName[name: fileName]; RETURN[fullFName.Replace[cp.ext.start, cp.ext.length, extension]]}; KeyVal: PROC[list: CommandUtil.PairList, key: Rope.ROPE, delete: BOOL_TRUE] RETURNS[Rope.ROPE] = INLINE {RETURN [CommandUtil.KeyValue[key, list, delete]]}; pgsVersion: PUBLIC TimeStamp.Stamp _ [net: 'c.ORD, host: 'p.ORD, time: 000F0003h]; <<* * * * * * HERE IT BEGINS * * * * * *>> NoSource: PUBLIC ERROR = CODE; LockedSource: PUBLIC ERROR = CODE; BadSemantics: PUBLIC ERROR = CODE; Generate: PUBLIC PROC[ source: Rope.ROPE, args, results: CommandUtil.PairList, switches: Rope.ROPE, startPhase: PROC[PGSOps.PGSPhase] RETURNS[BOOL], princOps: BOOL] RETURNS[success, warnings: BOOL] = { alto: BOOL _ ~princOps; long: BOOL_ princOps; printGrammar: BOOL _ TRUE; bcd: BOOL _ FALSE; scratchExists: BOOL _ FALSE; typeId, tableId, exportId: Rope.ROPE _ NIL; sourceName _ source; objectName _ gfName _ NIL; <> BEGIN nR: CARDINAL _ CommandUtil.ListLength[results]; IF (defsName _ KeyVal[results, "defs"]) # NIL THEN nR _ nR - 1; SELECT TRUE FROM (objectName _ KeyVal[results, "bcd"]) # NIL => {bcd _ TRUE; nR _ nR - 1}; (objectName _ KeyVal[results, "binary"]) # NIL => {bcd _ FALSE; nR _ nR - 1}; ENDCASE; IF (gfName _ KeyVal[results, "grammar"]) # NIL THEN nR _ nR - 1; IF nR # 0 THEN GO TO badSemantics; END; SetRoot[IF objectName # NIL THEN objectName ELSE sourceName]; IF switches # NIL THEN { sense: BOOL _ TRUE; FOR i: INT IN [0 .. switches.Length[]) DO SELECT switches.Fetch[i] FROM '-, '~ => sense _ ~sense; 'a, 'A => {alto _ sense; sense _ TRUE}; 'l, 'L => {long _ sense; sense _ TRUE}; 'g, 'G => {printGrammar _ sense; sense _ TRUE}; ENDCASE; ENDLOOP}; startTime _ BasicTime.Now[]; warningsLogged _ warnings _ FALSE; sourceName _ CommandUtil.SetExtension[sourceName, "pgs"]; IF sourceName.Fetch[sourceName.Length[]-1] = '. THEN sourceName _ Rope.Substr[sourceName, 0, sourceName.Length[]-1]; IF TestExtension[sourceName, "pgs"] THEN { inputName: Rope.ROPE ~ sourceName; sourceName _ Rope.Concat[GetRoot[inputName], ".mesa"]; [] _ startPhase[$format]; sourcestr _ FS.StreamOpen[inputName, $read ! FS.Error => IF error.group=lock THEN GOTO lockedSource ELSE GOTO noSource]; outStream _ outstr _ FS.StreamOpen[sourceName, $create]; [table: tableId, type: typeId, export: exportId] _ PGSConDefs.Format[ ! PGSFail => {GOTO formatFailed}]; <> <> sourceVersion _ [0, 0, CreateTime[outstr]]; closeoutstream[]; IO.Close[sourcestr]; sourcestr _ NIL; <> gfName _ IF printGrammar THEN SetFileName[gfName, IF tableId.Length[] # 0 THEN tableId ELSE rootName, "grammar"] ELSE "pgs.scratch$"; outStream _ outstr _ FS.StreamOpen[gfName, $create]; PGSConDefs.PrintGrammar[]; closeoutstream[]; IF ~printGrammar THEN scratchExists _ TRUE; <> sourcestr _ FS.StreamOpen[gfName, $read]; <> IF typeId.Length[] = 0 AND defsName # NIL THEN typeId _ GetRoot[defsName]; IF objectName = NIL THEN { bcd _ TRUE; IF tableId.Length[] # 0 THEN objectName _ tableId ELSE objectName _ Rope.Concat[rootName, "PGSTable"]} EXITS formatFailed => { closeoutstream[]; closeerrstream[]; seterrstream[]; outstring["\nDirectives incorrect or out of sequence\n"]; GO TO fail} } ELSE { sourcestr _ FS.StreamOpen[sourceName, $read ! FS.Error => {GO TO noSource}]; sourceVersion _ [0, 0, CreateTime[sourcestr]]; IF objectName = NIL THEN objectName _ rootName; <> typeId _ Rope.Concat[rootName, "PGSTable"]}; IF defsName = NIL THEN { IF typeId.Length[] # 0 THEN defsName _ typeId ELSE defsName _ Rope.Concat[rootName, "PGSTableType"]}; defsName _ CommandUtil.SetExtension[defsName, "mesa"]; objectName _ CommandUtil.SetExtension[objectName, IF bcd THEN "bcd" ELSE "binary"]; outstr _ errstr _ NIL; sourceOrigin _ IO.GetIndex[sourcestr]; <> [] _ startPhase[$lalr]; objectVersion _ OSMiscOps.GenerateUniqueId[]; success _ P1.Parse[sourcestr, Logger, TRUE].nErrors = 0; IO.Close[sourcestr]; closeoutstream[]; <> <> IF success AND (flags[lists] OR flags[printLALR] OR flags[printLR]) THEN { success _ PGSConDefs.LALRGen[ ! PGSFail => {success _ FALSE; CONTINUE}]; IF success AND flags[lists] THEN { InitBcd: PROC = { PGSConDefs.WriteBcdHeader[ outstr, tableId, objectName, IF Rope.Equal[exportId, "SELF"] THEN NIL ELSE exportId, KeyVal[args, exportId, FALSE], alto]}; closeoutstream[]; -- flush output from LALRGen outstr _ FS.StreamOpen[objectName]; -- for reinput success _ IF exportId.Length[] # 0 THEN PGSConDefs.TabGen[prefix:InitBcd, suffix:PGSConDefs.FixupBcdHeader] ELSE PGSConDefs.TabGen[NIL, NIL]; IF ~success THEN closewordstream[] ELSE { closeoutstream[]; -- flush tabgen output outStream _ outstr _ FS.StreamOpen[defsName, $create]; PGSConDefs.OutModule[typeId, defsName, long]; closeoutstream[]}}}; closeerrstream[]; warnings _ warningsLogged; EXITS badSemantics => ERROR BadSemantics; noSource => ERROR NoSource; lockedSource => ERROR LockedSource; fail => {closeerrstream[]; success _ FALSE} }; <> P1.InstallParseTable[LOOPHOLE[PrincOpsUtils.Codebase[LOOPHOLE[PGSParseData]]]]; }.