DIRECTORY Asserting, Cucumber, FS, IO, Rope, OrderedSymbolTableRef, RoseDisplayInsides, RoseTypes, RoseRun, RoseStateIO, SafeStorage; RoseStateIOImpl: PROGRAM IMPORTS Asserting, Cucumber, FS, IO, OrderedSymbolTableRef, RoseDisplayInsides, RoseRun, RoseTypes, SS: SafeStorage EXPORTS RoseStateIO = BEGIN ROPE: TYPE = Rope.ROPE; Cell: TYPE = RoseTypes.Cell; Dir: TYPE = Cucumber.Direction; Save: PUBLIC PROC [cell: Cell, fileName: ROPE] RETURNS [errMsg: ROPE] = BEGIN file: IO.STREAM _ FS.StreamOpen[fileName: fileName, accessOptions: create]; errMsg _ NIL; Cucumber.Transfer[what: cell, where: file, direction: out !Cucumber.Error => {errMsg _ msg; CONTINUE}]; file.Close[]; END; Restore: PUBLIC PROC [cell: Cell, fileName: ROPE] RETURNS [errMsg: ROPE] = BEGIN file: IO.STREAM _ FS.StreamOpen[fileName: fileName, accessOptions: read]; errMsg _ NIL; Cucumber.Transfer[what: cell, where: file, direction: in !Cucumber.Error => {errMsg _ msg; CONTINUE}]; IF errMsg # NIL THEN errMsg _ IO.PutFR["at %g: %g", IO.int[file.GetIndex[]], IO.rope[errMsg]]; file.Close[]; END; cellHandler: Cucumber.Handler _ NEW [Cucumber.HandlerRep _ [ PartTransfer: TransferCell]]; strHandler: Cucumber.Handler _ NEW [Cucumber.HandlerRep _ [ PartTransfer: TransferStructure]]; TransferCell: Cucumber.PartTransferProc = BEGIN cell: Cell _ NARROW[whole]; str: RoseTypes.Structure _ IF cell.parent # NIL THEN RoseTypes.ContainingStr[cell] ELSE NIL; IF (str # NIL) AND (cell = str.mirror) THEN ERROR; SELECT part.first FROM $type => NULL; $nextInstance => NULL; $sim => NULL; $parent => NULL; $leftChild => NULL; $rightSibling => NULL; $firstInternalNode => NULL; $internalNodes => NULL; $components => TransferComponents[cell, where, direction]; $interfaceNodes => NULL; $props => IF direction = out THEN CheckCellProps[cell]; $realCellStuff => IF cell.substantiality = Real THEN TransferRealCellStuff[cell, where, direction]; ENDCASE => ERROR; END; CheckCellProps: PROC [cell: Cell] = BEGIN FOR al: RoseTypes.Assertions _ cell.other, al.rest WHILE al # NIL DO key: Asserting.Term _ Asserting.RelnOf[al.first]; rest: Asserting.Terms _ Asserting.TermsOf[al.first]; IF key # NIL THEN WITH key SELECT FROM x: RoseDisplayInsides.Display => LOOP; ENDCASE; SELECT key FROM $ExpandDeciderClosure, RoseDisplayInsides.cellStateDisplayProp => LOOP; ENDCASE; IF rest # NIL AND rest.first # NIL THEN ERROR Cucumber.Error[IO.PutFR["%g has a %g relation, and I don't know what to do with it", IO.rope[cell.name], IO.refAny[key]]]; ENDLOOP; END; TransferComponents: PROC [cell: Cell, where: IO.STREAM, direction: Dir] = BEGIN WriteCell: SAFE PROC [asAny: REF ANY] RETURNS [stop: BOOLEAN] = TRUSTED BEGIN component: Cell _ NARROW[asAny]; where.PutF["%g ", IO.refAny[component.name]]; Cucumber.Transfer[component, where, out]; stop _ FALSE; END; SELECT direction FROM in => DO name: ROPE _ NARROW[where.GetRefAny[]]; component: Cell; IF name = NIL THEN EXIT; component _ NARROW[cell.components.Lookup[name]]; IF component = NIL THEN ERROR Cucumber.Error[IO.PutFR["component %g not found", IO.rope[name]]]; Cucumber.Transfer[component, where, direction]; ENDLOOP; out => BEGIN IF cell.components # NIL THEN cell.components.EnumerateIncreasing[WriteCell]; where.PutRope["NIL "]; END; ENDCASE => ERROR; END; TransferWords: PUBLIC PROC [wp: RoseTypes.WordPtr, wordCount: CARDINAL, stream: IO.STREAM, direction: Cucumber.Direction] = BEGIN SELECT direction FROM in => { FOR i: CARDINAL IN [0 .. wordCount) DO card: CARDINAL _ stream.GetCard[!SS.NarrowRefFault => ERROR Cucumber.Error["Not a CARDINAL"]]; TRUSTED {(wp + i)^ _ card}; ENDLOOP; }; out => { FOR i: CARDINAL IN [0 .. wordCount) DO TRUSTED {stream.PutF["%g ", IO.card[(wp + i)^]]}; ENDLOOP; }; ENDCASE => ERROR; END; TransferRealCellStuff: PROC [cell: Cell, where: IO.STREAM, direction: Dir] = BEGIN ReadIO: RoseRun.ModifyProc = TRUSTED {TransferWords[cell.realCellStuff.newIOAsWP, cell.type.ioWordCount, where, in]}; SELECT direction FROM in => BEGIN hasState: BOOLEAN; scheduled: BOOLEAN _ where.GetBool[!SS.NarrowRefFault => ERROR Cucumber.Error["Not a BOOLEAN"]]; IF cell.parent # NIL THEN RoseRun.AllowToModify[cell, ReadIO] ELSE [] _ ReadIO[cell]; hasState _ where.GetBool[!SS.NarrowRefFault => ERROR Cucumber.Error["Not a BOOLEAN"]]; IF hasState # (cell.realCellStuff.state # NIL) THEN ERROR Cucumber.Error[IO.PutFR["disagreement on emptiness of state of %g", IO.rope[cell.name]]]; IF hasState THEN Cucumber.Transfer[cell.realCellStuff.state, where, in]; END; out => BEGIN hasState: BOOLEAN _ cell.realCellStuff.state # NIL; where.PutF["%g ", IO.bool[cell.realCellStuff.schedNext # RoseTypes.notInCellList]]; TransferWords[cell.realCellStuff.newIOAsWP, cell.type.ioWordCount, where, out]; where.PutF["%g ", IO.bool[hasState]]; IF hasState THEN Cucumber.Transfer[cell.realCellStuff.state, where, out]; END; ENDCASE => ERROR; END; TransferStructure: PROC [whole: REF ANY, part: Cucumber.Path, where: IO.STREAM, direction: Cucumber.Direction, data: REF ANY] --Cucumber.PartTransferProc-- = { str: RoseTypes.Structure _ NARROW[whole]; SELECT part.first FROM $container, $schedFirst, $schedLast, $firstNeeded, $insideNodes, $nextPerturbed, $nextWasPerturbed, $firstPerturbed, $firstAffected => NULL; $mirror => NULL; ENDCASE => ERROR Cucumber.Error[IO.PutFR["Unexpected part %g of Structure", IO.refAny[part]]] }; Setup: PROC = BEGIN cellHandler.Register[CODE[RoseTypes.CellRep]]; strHandler.Register[CODE[RoseTypes.StructureRep]]; END; Setup[]; END. Δ[Indigo]2.6>Rosemary.df=>RoseStateIOImpl.Mesa Last Edited by: Spreitzer, September 6, 1984 3:33:48 pm PDT Cucumber.Transfer[what: str.mirror, where: where, direction: direction]; Κ ˜J™7J™