GenerateClient.mesa
Copyright Ó 1986, 1987 by Xerox Corporation. All rights reserved.
Bhargava, August 10, 1986 1:12:31 pm PDT
Bill Jackson (bj) June 11, 1987 1:21:16 am PDT
Demers, January 5, 1987 1:32:49 am PST
DIRECTORY
BasicTime USING [],
FS USING [StreamOpen],
IO USING [int, rope, Close, PutF, PutRope, STREAM],
Rope USING [ROPE, Concat, Equal],
SiroccoPrivate USING [AquireState, CComponent, CType, FileHeader, GetMProcName, GetUProcName, GenerateUMProcs, Handle, InterfaceItem, MakeUpName, Marshal, Nest, TABLES, UMProcNameProc, UnDo, UnMarshal],
SymTab USING [EachPairAction, Erase, Fetch, GetSize, Insert, Pairs, Val];
GenerateClient: CEDAR PROGRAM
IMPORTS Rope, IO, FS, SiroccoPrivate, SymTab
EXPORTS SiroccoPrivate ~ {
OPEN SiroccoPrivate;
ROPE: TYPE ~ Rope.ROPE;
GenCImpl: PUBLIC PROC [ ] ~ {
failure: BOOLEAN;
programKey: ROPE;
programKeyWD: ROPE;
cImplStream: IO.STREAM;
allTheTables: TABLES;
h: Handle;
CollectProcsAndErrors: SymTab.EachPairAction ~ {
entry: REF InterfaceItem ← NARROW [val];
successful: BOOLEAN;
type: CType;
value1: SymTab.Val;
[successful, value1] ← SymTab.Fetch[allTheTables.condensedTypeTable, entry.type];
type ← NARROW [value1];
SELECT type.class FROM
error => [] ← SymTab.Insert[allTheTables.errors, key, val];
proc => [] ← SymTab.Insert[allTheTables.procedures, key, val];
ENDCASE;
RETURN[FALSE];
};
GenerateRemoteProc: SymTab.EachPairAction ~ {
name: ROPENARROW [key];
entry: REF InterfaceItem ← NARROW [val];
list: CComponent;
successful: BOOLEAN;
value1: SymTab.Val;
type: CType;
unDoneCanonicalTypeName: ROPE;
[successful, value1] ← SymTab.Fetch[allTheTables.condensedTypeTable, entry.type];
type ← NARROW[value1];
unDoneCanonicalTypeName SiroccoPrivate.UnDo[entry.type, programKey];
IF Rope.Equal[name, unDoneCanonicalTypeName] THEN unDoneCanonicalTypeName ← SiroccoPrivate.MakeUpName[name, "Type", allTheTables];
IO.PutF[cImplStream, Nest["", 1]];
IO.PutF[cImplStream, Nest["%g: PUBLIC %g ~ {", 2],
IO.rope[name], IO.rope[unDoneCanonicalTypeName]];
IO.PutF[cImplStream, Nest["PutArgs: CrRPC.PutArgsProc ~ {", 3]];
list ← type.children;
IF (list = NIL)
THEN IO.PutF[cImplStream, Nest["NULL", 3]]
ELSE {
FOR loopindex: CARD IN [0..type.bound) DO
[successful, value1] ← SymTab.Fetch[allTheTables.condensedTypeTable, list.type];
type ← NARROW[value1];
Marshal[h, cImplStream, list.name, type, list.type, GetMProcName, TRUE, 3];
IO.PutRope[cImplStream, Nest[NIL, 3]];
list ← list.sibling;
ENDLOOP;
};
IO.PutF[cImplStream, Nest["};", 2]];
IO.PutF[cImplStream, Nest["GetResults: CrRPC.GetResultsProc ~ {", 3]];
IF (list = NIL)
THEN IO.PutF[cImplStream, Nest["NULL", 3]];
WHILE (list # NIL) DO
[successful, value1] ← SymTab.Fetch[allTheTables.condensedTypeTable, list.type];
type ← NARROW [value1];
UnMarshal[h, cImplStream, list.name, type, list.type, GetUProcName, TRUE, 3];
IO.PutF[cImplStream, Nest[NIL, 3]];
list ← list.sibling;
ENDLOOP;
IO.PutF[cImplStream, Nest["};", 3]];
IO.PutF[cImplStream, Nest["", 2]];
IO.PutF[cImplStream, Nest["CrRPC.Call[h~h, remotePgm~%g, remotePgmVersion~%g, remoteProc~%g, putArgs~PutArgs, getResults~GetResults, getError~GetError];", 2],
IO.int[h.programNo],
IO.int[h.versionNo],
IO.rope[entry.constant]
];
IO.PutF[cImplStream, Nest["};", 1]];
};
GenerateErrorDefinition: SymTab.EachPairAction ~ {
name: ROPENARROW [key];
entry: REF InterfaceItem ← NARROW [val];
successful: BOOLEAN;
type: CType;
value1: SymTab.Val;
unDoneCanonicalTypeName: ROPE;
[successful, value1] ← SymTab.Fetch[allTheTables.condensedTypeTable, entry.type];
type ← NARROW[value1];
unDoneCanonicalTypeName SiroccoPrivate.UnDo[entry.type, programKey];
IF Rope.Equal[name, unDoneCanonicalTypeName] THEN
unDoneCanonicalTypeName ← SiroccoPrivate.MakeUpName[name, "Type", allTheTables];
IO.PutF[cImplStream, Nest["", 1]];
IO.PutF[cImplStream, Nest["%g: PUBLIC %g ~ CODE;", 1],
IO.rope[name], IO.rope[unDoneCanonicalTypeName]];
};
GenerateErrorCase: SymTab.EachPairAction ~ {
entry: REF InterfaceItem ← NARROW [val];
name: ROPENARROW [key];
successful: BOOLEAN;
type: CType;
value1: SymTab.Val;
IF Rope.Equal[entry.constant , ""] THEN RETURN;
IO.PutF[cImplStream, "%g => ",
IO.rope[entry.constant]
];
[successful, value1] ← SymTab.Fetch[allTheTables.condensedTypeTable, entry.type];
type ← NARROW[value1];
IF (type.children = NIL)
THEN {
IO.PutF[cImplStream, Nest["ERROR %g[];", 3],
IO.rope[name]
];
}
ELSE {
IO.PutF[cImplStream, Nest["{", 4]];
FOR list: CComponent ← type.children, list.sibling WHILE (list # NIL) DO
IO.PutF[cImplStream, Nest["%g: %g;", 4],
IO.rope[list.name],
IO.rope[SiroccoPrivate.UnDo[list.type, programKey]]
];
ENDLOOP;
FOR list: CComponent ← type.children, list.sibling WHILE (list # NIL) DO
[successful, value1] ← SymTab.Fetch[allTheTables.condensedTypeTable, list.type];
UnMarshal[h, cImplStream, list.name, NARROW [value1], list.type, GetUProcName, TRUE, 3];
IO.PutF[cImplStream, Nest["", 4]];
ENDLOOP;
IO.PutF[cImplStream, "ERROR %g[",
IO.rope[name],
];
FOR list: CComponent ← type.children, list.sibling WHILE (list # NIL) DO
IO.PutRope[cImplStream, list.name];
IF list.sibling # NIL THEN IO.PutRope[cImplStream, ", "];
ENDLOOP;
IO.PutF[cImplStream, Nest["]", 4]];
IO.PutF[cImplStream, Nest["};", 3]];
};
};
Heading: PROC [out: IO.STREAM] ~ {
PutDirectory: SymTab.EachPairAction ~ {
interface: ROPE ~ NARROW [val];
IO.PutF[out, Nest["%g,", 1],
IO.rope[interface]
];
};
SiroccoPrivate.FileHeader[out, Rope.Concat[programKeyWD,"ClientImpl.Mesa"]];
IO.PutF[out, Nest["DIRECTORY", 1]];
IO.PutF[out, Nest["CrRPC,", 1]];
failure ← SymTab.Pairs[allTheTables.directory, PutDirectory];
IO.PutF[out, Nest["%g;", 0], IO.rope[programKeyWD]];
IO.PutF[out, Nest["", 0]];
IO.PutF[out, Nest["%gClientImpl: CEDAR PROGRAM", 1], IO.rope[programKeyWD]];
IO.PutF[out, Nest["IMPORTS CrRPC", 1]];
IO.PutF[out, Nest["EXPORTS %g ~ {", 1], IO.rope[programKeyWD]];
IO.PutF[out, Nest["OPEN %g;", 0], IO.rope[programKeyWD]];
IO.PutF[out, Nest["", 0]];
};
h ← SIGNAL SiroccoPrivate.AquireState[];
programKey ← h.programKey;
programKeyWD ← h.programKeyWD;
allTheTables ← h.allTheTables;
cImplStream ← FS.StreamOpen[Rope.Concat[programKeyWD,"ClientImpl.Mesa"], $create];
Heading[cImplStream];
SymTab.Erase[allTheTables.procedures];
SymTab.Erase[allTheTables.errors];
SymTab.Erase[allTheTables.workTable];
failure ← SymTab.Pairs[allTheTables.localTable, CollectProcsAndErrors];
IF (SymTab.GetSize[allTheTables.errors] = 0)
THEN {
IO.PutF[cImplStream, Nest["GetError: CrRPC.GetErrorProc ~ {", 2]];
IO.PutF[cImplStream, Nest["ERROR CrRPC.Error[h, remoteError, \"%g\"];", 2],
IO.rope["Unexpected Remote Error"]
];
IO.PutF[cImplStream, Nest["};", 1]];
}
ELSE {
IO.PutF[cImplStream, Nest["-- Errors", 1]];
IO.PutF[cImplStream, Nest["", 1]];
failure ← SymTab.Pairs[allTheTables.errors, GenerateErrorDefinition];
IO.PutF[cImplStream, Nest["", 0]];
IO.PutF[cImplStream, Nest["-- GetErrorProc", 1]];
IO.PutF[cImplStream, Nest["", 1]];
IO.PutF[cImplStream, Nest["GetError: CrRPC.GetErrorProc ~ {", 2]];
IO.PutF[cImplStream, Nest["SELECT errNum FROM", 3]];
failure ← SymTab.Pairs[allTheTables.errors, GenerateErrorCase];
IO.PutF[cImplStream, Nest["ENDCASE => {", 4]];
IO.PutF[cImplStream, Nest["ERROR CrRPC.Error[h, remoteError, \"%g\"];", 4],
IO.rope["Unexpected Remote Error"]
];
IO.PutF[cImplStream, Nest["};", 2]];
IO.PutF[cImplStream, Nest["};", 1]];
};
IO.PutRope[cImplStream, Nest[NIL, 0]];
IO.PutRope[cImplStream, Nest["-- Remote Procedures --", 1]];
failure ← SymTab.Pairs[allTheTables.procedures, GenerateRemoteProc];
IO.PutF[cImplStream, Nest[NIL, 0]];
IF (SymTab.GetSize[allTheTables.workTable] > 0) THEN {
IO.PutF[cImplStream, Nest["-- Unmarshal / Marshal Procs --", 1]];
IO.PutF[cImplStream, Nest[NIL, 1]];
GenerateUMProcs[h, cImplStream, 1];
IO.PutF[cImplStream, Nest[NIL, 0]];
};
IO.PutF[cImplStream, Nest["}...", 0]];
IO.Close[cImplStream];
};
}.