IODefsImpl.mesa
Last Edited by: McCreight, June 13, 1985 4:13:18 pm PDT
DIRECTORY
BasicTime, IO, IODefs, Menus, MessageWindow, Process, Rope, ViewerClasses, ViewerEvents, ViewerIO, ViewerOps;
IODefsImpl: CEDAR MONITOR
IMPORTS IO, Menus, MessageWindow, Process, ViewerEvents, ViewerIO, ViewerOps
EXPORTS IODefs =
BEGIN
log: PUBLIC IO.STREAMNIL;
WriteString: PUBLIC PROC [s: Rope.ROPE] =
{Log[].PutRope[s ! IO.Error => {ResetLog[]; RETRY}]};
WriteLine: PUBLIC PROC [s: Rope.ROPE] =
{Log[].PutF["%g\n", IO.rope[s] ! IO.Error => {ResetLog[]; RETRY}]};
WriteChar: PUBLIC PROC [c: CHARACTER] =
{Log[].PutChar[c ! IO.Error => {ResetLog[]; RETRY}]};
WriteDecimal: PUBLIC PROC [n: INT] =
{Log[].PutF["%g", IO.int[n] ! IO.Error => {ResetLog[]; RETRY}]};
WriteReal: PUBLIC PROC [r: REAL] =
{Log[].PutF["%g", IO.real[r] ! IO.Error => {ResetLog[]; RETRY}]};
PrintTime: PUBLIC PROC [msg: Rope.ROPENIL] =
{Log[].PutF["%g %g\n", IO.rope[msg], IO.time[] ! IO.Error => {ResetLog[]; RETRY}]};
PostIt: PUBLIC ENTRY PROC [s: Rope.ROPE] =
{ENABLE UNWIND => NULL; postee ← s; CheckStop[]};
Log: PROC RETURNS [ IO.STREAM ] =
BEGIN
WHILE log = NIL DO
menuEntry: Menus.MenuEntry = Menus.CreateEntry[name: "STOP!", proc: NoticeStop, guarded: TRUE];
viewer: ViewerClasses.Viewer;
doStop ← FALSE;
log ← ViewerIO.CreateViewerStreams[name: "MPC Log", backingFile: "MPC.log"].out;
viewer ← ViewerIO.GetViewerFromStream[log];
[] ← Menus.InsertMenuEntry[menu: viewer.menu, entry: menuEntry];
ViewerOps.PaintViewer[viewer, menu];
[] ← ViewerEvents.RegisterEventProc[proc: CloseOutputStream, event: destroy, filter: viewer];
log.PutF["MPC.log of %g...\n\n", IO.time[]];
ENDLOOP;
CheckStop[];
RETURN[log];
END;
doStop: BOOLFALSE;
CheckStop: PROC = {IF doStop THEN {doStop ← FALSE; ERROR ABORTED}};
NoticeStop: PROC [parent: REF ANY, clientData: REF ANYNIL,
mouseButton: Menus.MouseButton ← red, shift, control: BOOLFALSE] -- Menus.ClickProc -- =
{doStop ← TRUE};
CloseOutputStream: PROC [viewer: ViewerClasses.Viewer, event: ViewerEvents.ViewerEvent, before: BOOL] RETURNS [abort: BOOLFALSE] -- ViewerEvents.EventProc -- =
{ResetLog[]};
ResetLog: PROC = {IF log # NIL THEN log.Close[ ! IO.Error => CONTINUE ]; log ← NIL};
postee: Rope.ROPENIL;
posteeReady: CONDITION;
Poster: ENTRY PROC =
BEGIN
ENABLE UNWIND => NULL;
lastPostee: Rope.ROPENIL;
DO
IF log#NIL THEN log.Flush[ ! IO.Error => CONTINUE ];
IF postee # NIL OR lastPostee # NIL THEN
BEGIN
MessageWindow.Append[message: postee, clearFirst: TRUE];
lastPostee ← postee;
postee ← NIL;
END;
WAIT posteeReady;
ENDLOOP;
END;
TRUSTED
BEGIN
Process.InitializeCondition[condition: @posteeReady, ticks: Process.SecondsToTicks[2]];
Process.Detach[FORK Poster[]];
END;
END.