-- edited by Teitelman June 9, 1982 7:35 am -- edited by McGregor June 11, 1982 11:08 am DIRECTORY ViewerIO, IO, Rope, ViewerClasses, TypeScript; ViewerIOImpl: PROGRAM IMPORTS IO, TypeScript EXPORTS IO, ViewerIO SHARES IO = BEGIN Viewer: TYPE = ViewerClasses.Viewer; ViewerStreamData: TYPE = REF ViewerStreamDataRecord; ViewerStreamDataRecord: TYPE = RECORD[ viewer: Viewer, echoTo: IO.STREAM _ NIL ]; ViewerInStreamProcs: REF IO.StreamProcs _ IO.CreateRefStreamProcs[ getChar: ViewerGetChar, close: ViewerClose, endOf: ViewerEndOf, charsAvail: ViewerCharsAvail, setEcho: ViewerSetEcho, userAbort: ViewerUserAbort, name: "Viewers Input" ]; ViewerOutStreamProcs: REF IO.StreamProcs _ IO.CreateRefStreamProcs[ putChar: ViewerPutChar, putBlock: ViewerPutBlock, close: ViewerClose, endOf: ViewerEndOf, eraseChar: ViewerEraseChar, userAbort: ViewerUserAbort, name: "Viewers Output" ]; CreateTTYStreams: PUBLIC SAFE PROC [name: Rope.ROPE] RETURNS [in: IO.STREAM, out: IO.STREAM] = TRUSTED {[in, out] _ CreateViewerStreams[name]; }; CreateViewerStreams: PUBLIC PROC [name: Rope.ROPE, viewer: Viewer _ NIL, backingFile: Rope.ROPE _ NIL] RETURNS [in: IO.STREAM, out: IO.STREAM] = {OPEN IO; IF viewer = NIL THEN viewer _ TypeScript.Create[info: [name: name]]; {in _ CreateProcsStream[streamProcs: ViewerInStreamProcs, streamData: NEW[ViewerStreamDataRecord _ [viewer: viewer]] ]; out _ CreateProcsStream[streamProcs: ViewerOutStreamProcs, streamData: NEW[ViewerStreamDataRecord _ [viewer: viewer]] ]; IF backingFile # NIL THEN out _ IO.CreateDribbleStream[stream: out, dribbleTo: IO.CreateFileStream[fileName: backingFile, accessOptions: overwrite], flushEveryNChars: 256]; [] _ SetEcho[in, out]; }; }; ViewerGetChar: SAFE PROCEDURE [self: IO.STREAM] RETURNS [char: CHARACTER] = TRUSTED BEGIN data: ViewerStreamData _ NARROW[self.streamData]; IF data.viewer.destroyed THEN IO.Error[StreamClosed]; char _ TypeScript.GetChar[data.viewer]; IF data.echoTo # NIL THEN IO.PutChar[data.echoTo, char]; END; -- of ViewerGetChar ViewerPutChar: SAFE PROCEDURE[self: IO.STREAM, char: CHARACTER] = TRUSTED BEGIN data: ViewerStreamData _ NARROW[self.streamData]; IF data.viewer.destroyed THEN IO.Error[StreamClosed]; TypeScript.PutChar[data.viewer, char]; END; -- of ViewerPutChar ViewerPutBlock: SAFE PROCEDURE[self: IO.STREAM, block: REF READONLY TEXT, startIndex: NAT, stopIndexPlusOne: NAT] = TRUSTED BEGIN data: ViewerStreamData _ NARROW[self.streamData]; IF data.viewer.destroyed THEN IO.Error[StreamClosed]; TypeScript.PutText[ts: data.viewer, text: block, start: startIndex, stopPlusOne: stopIndexPlusOne]; END; -- of ViewerPutChar ViewerReset: SAFE PROCEDURE[self: IO.STREAM] = TRUSTED BEGIN data: ViewerStreamData _ NARROW[self.streamData]; TypeScript.Reset[data.viewer]; END; -- of ViewerClose ViewerClose: SAFE PROCEDURE[self: IO.STREAM, abort: BOOLEAN] = TRUSTED BEGIN data: ViewerStreamData _ NARROW[self.streamData]; IF ~data.viewer.destroyed THEN TypeScript.Destroy[data.viewer]; END; -- of ViewerClose ViewerEndOf: SAFE PROCEDURE[self: IO.STREAM] RETURNS [BOOLEAN] = CHECKED BEGIN data: ViewerStreamData _ NARROW[self.streamData]; IF data.viewer.destroyed THEN IO.Error[StreamClosed]; RETURN[FALSE]; END; -- ViewerEndOf ViewerCharsAvail: SAFE PROCEDURE[self: IO.STREAM] RETURNS [BOOLEAN] = TRUSTED BEGIN data: ViewerStreamData _ NARROW[self.streamData]; IF data.viewer.destroyed THEN IO.Error[StreamClosed]; RETURN[TypeScript.CharsAvailable[data.viewer]]; END; -- ViewerCharsAvail ViewerEraseChar: SAFE PROCEDURE[self: IO.STREAM, char: CHARACTER] = TRUSTED BEGIN data: ViewerStreamData _ NARROW[self.streamData]; IF data.viewer.destroyed THEN IO.Error[StreamClosed]; TypeScript.BackSpace[data.viewer]; END; -- of ViewerEraseChar ViewerSetEcho: SAFE PROCEDURE[self: IO.STREAM, echoTo: IO.STREAM] RETURNS[oldEcho: IO.STREAM] = CHECKED BEGIN data: ViewerStreamData _ NARROW[self.streamData]; IF data.viewer.destroyed THEN IO.Error[StreamClosed]; oldEcho _ data.echoTo; data.echoTo _ echoTo; END; -- of ViewerSetEcho -- until Andrew gets around to doing this in a more general fashion, this will allow aborting of typeout to a stream that is connected to a typescript/exec ViewerUserAbort: SAFE PROC [self: IO.STREAM] RETURNS [abort: BOOLEAN] = TRUSTED {data: ViewerStreamData _ NARROW[self.streamData]; RETURN[TypeScript.UserAbort[data.viewer]]; }; END. March 24, 1982 7:46 pm W. Teitelman. Fixed Close to check if viewer already destroyed. Added name argument to CreateRefStreamProcs. 13-Apr-82 14:05:22 W. Teitelman. Added checks for whether viewer was destroyed, and if so, raised IO error May 27, 1982 2:49 pm W. Teitelman. Changed name of IOStream to IO. Made changes relating to IO being in the Safe language June 1, 1982 6:01 pm W. Teitelman. Added CheckForAbort.