PupEchoServerImpl.mesa
Hal Murray June 3, 1985 8:44:31 pm PDT
DIRECTORY
GermSwap USING [switches],
PupDefs USING [PupAddress, PupBuffer, PupRouterSendThis, PupSocket, PupSocketDestroy, PupSocketKick, PupSocketMake, ReturnFreePupBuffer, ReturnPup, SwapPupSourceAndDest, veryLongWait],
PupTypes USING [echoSoc, fillInPupAddress],
PupEchoServer USING [echoStatsReply, echoStatsRequest, EchoStatsEntry, echoVersion],
PupWireFormat USING [MesaToBcplLongNumber];
PupEchoServerImpl: CEDAR MONITOR
IMPORTS
GermSwap, PupDefs, PupWireFormat
EXPORTS PupEchoServer =
BEGIN
Server data (global)
pupsEchoed: INT ← 0;
pleaseStopServer: BOOLEANFALSE;
server: PROCESSNIL;
serverSoc: PupDefs.PupSocket ← NIL;
Start: PUBLIC ENTRY PROC = {
IF server # NIL THEN RETURN;
pleaseStopServer ← FALSE;
server ← FORK Server[]; };
Stop: PUBLIC ENTRY PROC = TRUSTED {
IF server = NIL THEN RETURN;
pleaseStopServer ← TRUE;
IF server # NIL THEN {PupDefs.PupSocketKick[serverSoc]; JOIN server; };
server ← NIL; };
Server: PROC = TRUSTED {
serverSoc ← PupDefs.PupSocketMake[
PupTypes.echoSoc, PupTypes.fillInPupAddress, PupDefs.veryLongWait];
UNTIL pleaseStopServer DO
b: PupDefs.PupBuffer ← serverSoc.get[];
IF b # NIL THEN {
SELECT b.pupType FROM
echoMe => {
b.pupType ← iAmEcho;
PupDefs.SwapPupSourceAndDest[b];
PupDefs.PupRouterSendThis[b];
pupsEchoed ← pupsEchoed.SUCC; };
PupEchoServer.echoStatsRequest => {
EchoStatsEntry: TYPE = PupEchoServer.EchoStatsEntry;
ese: LONG POINTER TO EchoStatsEntry ← LOOPHOLE[@b.pupWords];
ese^ ← [
version: PupEchoServer.echoVersion,
pupsEchoed: PupWireFormat.MesaToBcplLongNumber[pupsEchoed]];
PupDefs.ReturnPup[
b, PupEchoServer.echoStatsReply, 2*SIZE[EchoStatsEntry]]; };
ENDCASE => PupDefs.ReturnFreePupBuffer[b]; };
ENDLOOP;
PupDefs.PupSocketDestroy[serverSoc];
serverSoc ← NIL; };
IF ~GermSwap.switches[c] THEN Start[];
END.