MispAlone.Mesa
Last Edited by: Spreitzer, July 30, 1985 3:26:30 pm PDT
Pavel, June 20, 1985 1:27:30 pm PDT
DIRECTORY
Commander,
EditedStream,
IO,
List,
Menus,
Misp,
Process,
ProcessProps,
ReadEvalPrint,
Rope,
ViewerClasses,
ViewerIO;
MispAlone: CEDAR PROGRAM
IMPORTS Commander, EditedStream, IO, List, Menus, Misp, Process, ProcessProps, --ReadEvalPrint,-- Rope, ViewerIO =
BEGIN
InterpreterData: TYPE = REF InterpreterDataRep;
InterpreterDataRep: TYPE = RECORD [
process: UNSAFE PROCESS,
stop: REF BOOL];
ReadEvalPrint: PROC [from, to: IO.STREAM, env: Misp.Environment, cwd: Rope.ROPE, stopRef: REF BOOL] =
BEGIN
InnerReadEvalPrint: PROC = {
raw, cooked: REF ANYNIL;
Flush: PROC = {
to.PutRope[" ... flushing input ... "];
WHILE from.CharsAvail[] > 0 DO [] ← from.GetChar[] ENDLOOP;
to.PutRope[" ... done flushing\n"];
};
DO {
ENABLE ABORTED => GOTO Abort;
to.PutF["%lMisp>%l ", IO.rope["b"], IO.rope["B"]];
raw ← from.GetRefAny[ !
IO.EndOfStream => EXIT;
IO.Error => {
IF ec = $StreamClosed THEN EXIT;
to.PutRope["IO Error on input"];
Flush[];
LOOP;
};
EditedStream.Rubout => {
to.PutRope[" -- <Del>\n"];
LOOP;
};
];
cooked ← Misp.Eval[raw, env, NIL !
Misp.Stop => {
to.PutF["Stopped, at stack = %g", IO.rope[Misp.PrintValRope[stack]]];
stopRef^ ← FALSE;
Flush[];
LOOP;
};
Misp.Error => {
to.PutF["%g\n Stack: %g\n", IO.rope[msg], IO.rope[Misp.PrintValRope[stack]]];
LOOP;
};
Misp.Throw => {
to.PutF["Uncaught Throw -- signal: %g, value: %g\n Stack: %g\n", IO.atom[atom], IO.rope[Misp.PrintValRope[value]], IO.rope[Misp.PrintValRope[stack]]];
LOOP;
};
];
to.PutF["%g\n", IO.rope[Misp.PrintValRope[cooked]]];
EXITS
Abort => {
to.PutRope[" ... aborted"];
Flush[];
};
} ENDLOOP;
cwd ← cwd;
};
ProcessProps.AddPropList[List.PutAssoc[$WorkingDirectory, cwd, NIL], InnerReadEvalPrint];
cwd ← cwd;
END;
MispCommand: Commander.CommandProc =
BEGIN
in, out: IO.STREAM;
v: ViewerClasses.Viewer;
env: Misp.Environment;
cwd: Rope.ROPENARROW[ProcessProps.GetProp[$WorkingDirectory]];
id: InterpreterData ← NEW [InterpreterDataRep ← [
process: NIL,
stop: NEW [BOOLFALSE]
]];
[in, out] ← ViewerIO.CreateViewerStreams[Rope.Cat["Misp Interpreter: WD = ", cwd]];
v ← ViewerIO.GetViewerFromStream[out];
Menus.AppendMenuEntry[v.menu, Menus.CreateEntry[name: "Stop", proc: Stop, clientData: id]];
Menus.AppendMenuEntry[v.menu, Menus.CreateEntry[name: "STOP!", proc: StopHard, clientData: id]];
env ← Misp.NewEnvironment[name: "Root", in: in, out: out, sizeGuess: 200, stop: [ShouldStop, id.stop]];
Misp.DefinePrimitives[env];
TRUSTED {Process.Detach[id.process ← FORK ReadEvalPrint[in, out, env, cwd, id.stop]]};
END;
ShouldStop: PROC [data: REF] RETURNS [abort: BOOLFALSE] --Interpreter.AbortProc-- = {
stop: REF BOOLNARROW[data];
abort ← stop # NIL AND stop^;
};
Stop: PROC [parent: REF ANY, clientData: REF ANYNIL,
mouseButton: Menus.MouseButton ← red, shift, control: BOOLFALSE] --Menus.ClickProc-- = {
id: InterpreterData ← NARROW[clientData];
id.stop^ ← TRUE;
};
StopHard: PROC [parent: REF ANY, clientData: REF ANYNIL,
mouseButton: Menus.MouseButton ← red, shift, control: BOOLFALSE] --Menus.ClickProc-- = {
id: InterpreterData ← NARROW[clientData];
TRUSTED {Process.Abort[id.process]};
};
MispCommand: Commander.CommandProc =
BEGIN
h: ReadEvalPrint.Handle;
env: Misp.Environment;
h ← ReadEvalPrint.CreateViewerEvaluator[
clientProc: EachLine,
prompt: "%lMisp>%l ",
info: [name: "Misp Interpreter", iconic: FALSE]];
env ← Misp.NewEnvironment[name: "Root (with IO)", in: h.in, out: h.out];
Misp.DefinePrimitives[env];
h.clientData ← env;
h.readABORTEDRope ← " -- <Read aborted>\n";
h.readIOSignalRope ← " -- <Del>\n";
h.evalABORTEDRope ← " ... Aborted\n";
h.evalUNWINDRope ← " ... Unwound\n";
TRUSTED {Process.Detach[FORK MispBase[h]]};
END;
MispBase: PROC [h: ReadEvalPrint.Handle] = {
DO
ReadEvalPrint.MainLoop[h: h, forkAndDetach: FALSE, properties: NIL !
Misp.Error => {
h.out.PutF["%g\nStack: ", IO.rope[msg]];
Misp.PrintVal[h.out, stack];
h.out.PutChar['\n];
ReadEvalPrint.Stop[h];
LOOP;
}
];
EXIT; -- Normal exit from the Main Loop
ENDLOOP;
};
EachLine: ReadEvalPrint.ClientProc = {
[h: ReadEvalPrint.Handle, command: ROPE] RETURNS [result: ROPE ← NIL]
env: Misp.Environment ← NARROW[h.clientData];
input: IO.STREAMIO.RIS[command];
raw, cooked: REF ANY;
DO
raw ← input.GetRefAny[ !
IO.EndOfStream => EXIT;
];
cooked ← Misp.Eval[raw, env, NIL];
Misp.PrintVal[h.out, cooked];
h.out.PutChar['\n];
ENDLOOP;
};
Commander.Register[
key: "Misp",
proc: MispCommand,
doc: "Opens a new viewer for interacting with the Misp interpreter"]
END.