-- OtherNodeImpl.Mesa
-- Written by Bill Paxton, May 1981
-- last written by McGregor. June 10, 1982 4:46 pm
DIRECTORY
OtherNode,
TextNode,
RefTab,
Rope;
OtherNodeImpl:
CEDAR PROGRAM
IMPORTS RefTab, TextNode
EXPORTS OtherNode =
BEGIN
OPEN OtherNode;
ROPE: TYPE = Rope.ROPE;
-- ***** Operations
ReaderProcRef: TYPE = REF ReaderProcRec;
ReaderProcRec: TYPE = RECORD [proc: ReadSpecsProc];
WriterProcRef: TYPE = REF WriterProcRec;
WriterProcRec: TYPE = RECORD [proc: WriteSpecsProc];
CopierProcRef: TYPE = REF CopierProcRec;
CopierProcRec: TYPE = RECORD [proc: CopyInfoProc];
readerTable: RefTab.Ref ← RefTab.Create[zone: TextNode.pZone];
writerTable: RefTab.Ref ← RefTab.Create[zone: TextNode.pZone];
copierTable: RefTab.Ref ← RefTab.Create[zone: TextNode.pZone];
Register:
PUBLIC
PROC [variety:
ATOM,
reader: ReadSpecsProc,
writer: WriteSpecsProc,
copier: CopyInfoProc] = {
-- registers these procs for this variety of node
-- they will be called by DoSpecs, GetSpecs, and CopyInfo
IF variety=NIL THEN RETURN;
[] ← RefTab.Store[readerTable,variety,TextNode.pZone.NEW[ReaderProcRec ← [reader]]];
[] ← RefTab.Store[writerTable,variety,TextNode.pZone.NEW[WriterProcRec ← [writer]]];
[] ← RefTab.Store[copierTable,variety,TextNode.pZone.NEW[CopierProcRec ← [copier]]] };
DoSpecs:
PUBLIC
PROC [n: RefOtherNode, specs:
ROPE] = {
-- used when reading files
-- calls the registered reader for this variety of node
-- sets n.info ← specs if no reader is registered
procRef: ReaderProcRef;
proc: ReadSpecsProc;
IF n.variety=
NIL
OR
(procRef ← NARROW[RefTab.Fetch[readerTable,n.variety].val])=NIL OR
(proc ← procRef.proc)=NIL
THEN n.info ← specs
ELSE proc[n,specs] };
GetSpecs:
PUBLIC
PROC [n: RefOtherNode]
RETURNS [specs:
ROPE] = {
-- used when writing files
-- calls the registered writer for this variety of node
-- if no writer is registered, returns n.info if it is a rope, NIL otherwise
procRef: WriterProcRef;
proc: WriteSpecsProc;
IF n.variety=
NIL
OR
(procRef ← NARROW[RefTab.Fetch[writerTable,n.variety].val])=NIL OR
(proc ← procRef.proc)=NIL
THEN
IF n.info=
NIL
THEN specs ←
NIL
ELSE
WITH n.info
SELECT
FROM
rope: ROPE => specs ← rope;
ENDCASE => specs ← NIL
ELSE specs ← proc[n] };
CopyInfo:
PUBLIC
PROC [old: RefOtherNode]
RETURNS [newinfo:
REF
ANY] = {
-- used when copying nodes
-- calls the registered copier for this variety of node
-- if no copier is registered, returns old.info
procRef: CopierProcRef;
proc: CopyInfoProc;
IF old.variety=
NIL
OR
(procRef ← NARROW[RefTab.Fetch[copierTable,old.variety].val])=NIL OR
(proc ← procRef.proc)=NIL
THEN newinfo ← old.info
ELSE newinfo ← proc[old] };
-- ***** Initialization
Start:
PUBLIC
PROC = {
};
END.