--MemoryExample.Mesa
--created by RoseTranslate from MemoryExample.Rose of April 13, 1984 11:58:06 am PST for Spreitzer.pa at April 13, 1984 11:58:18 am PST
DIRECTORY
RoseTypes, RoseCreate, BitOps, RoseRun, SwitchTypes, NumTypes;
MemoryExample: CEDAR PROGRAM
IMPORTS RoseCreate, BitOps, RoseRun, NumTypes, SwitchTypes =
BEGIN OPEN
RoseTypes, RoseRun;
--Signal Type decls
RegisterCells: PROC =
BEGIN
CreateMemoryPorts[];
[] ← RoseCreate.RegisterCellClass[className: "Memory",
expandProc: NIL,
ioCreator: CreateMemoryIO, initializer: InitializeMemory,
evals: [ValsChanged: MemoryValsChanged, PropQ: MemoryPropQ, PropUD: MemoryPropUD, EvalSimple: MemoryEvalSimple],
blackBox: NIL, stateToo: NIL,
ports: MemoryPorts,
drivePrototype: NEW [MemoryDrive]];
CreateDriverPorts[];
[] ← RoseCreate.RegisterCellClass[className: "Driver",
expandProc: NIL,
ioCreator: CreateDriverIO, initializer: InitializeDriver,
evals: [PropQ: DriverPropQ, PropUD: DriverPropUD, EvalSimple: DriverEvalSimple],
blackBox: NIL, stateToo: NIL,
ports: DriverPorts,
drivePrototype: NEW [DriverDrive]];
[] ← RoseCreate.RegisterCellClass[className: "MemoryExample",
expandProc: MemoryExampleExpand,
ioCreator: NIL, initializer: NIL,
evals: [],
blackBox: NIL, stateToo: NIL,
ports: MemoryExamplePorts,
drivePrototype: NIL];
END;
--explicitly requested CEDAR:
WordCount: CARDINAL = 4;
WordSize: CARDINAL = 4;
WordLines: TYPE = LONG POINTER TO ARRAY [0 .. WordCount) OF WordLine;
WordLine: TYPE = MACHINE DEPENDENT RECORD [
fill0(0:0..14): [0 .. 32768),
read(0:15..15): BOOL,
fill1(1:0..14): [0 .. 32768),
write(1:15..15): BOOL];
Word: TYPE = PACKED ARRAY [0 .. WordSize) OF BOOL;
CreateMemoryPorts: PROC = {MemoryPorts ← RoseCreate.PortsFromFile["MemoryExample.Memory.rosePorts"]};
MemoryIORef: TYPE = REF MemoryIORec;
MemoryIORec: TYPE = MACHINE DEPENDENT RECORD [
fill0(0:0..14): [0..32767],
Read0(0:15..15): BOOLEAN,
fill1(1:0..14): [0..32767],
Write0(1:15..15): BOOLEAN,
fill2(2:0..14): [0..32767],
Read1(2:15..15): BOOLEAN,
fill3(3:0..14): [0..32767],
Write1(3:15..15): BOOLEAN,
fill4(4:0..14): [0..32767],
Read2(4:15..15): BOOLEAN,
fill5(5:0..14): [0..32767],
Write2(5:15..15): BOOLEAN,
fill6(6:0..14): [0..32767],
Read3(6:15..15): BOOLEAN,
fill7(7:0..14): [0..32767],
Write3(7:15..15): BOOLEAN,
bitLines(8:0..63): PACKED ARRAY [0 .. 3] OF SwitchTypes.SwitchVal];
-- port indices:
MemoryBitLinesPortIndex: CARDINAL = 8;
MemoryDrive: TYPE = MACHINE DEPENDENT RECORD [
fill0(0:0..14): [0 .. 32768),
Read0(0:15..15): BOOLEAN,
fill1(1:0..14): [0 .. 32768),
Write0(1:15..15): BOOLEAN,
fill2(2:0..14): [0 .. 32768),
Read1(2:15..15): BOOLEAN,
fill3(3:0..14): [0 .. 32768),
Write1(3:15..15): BOOLEAN,
fill4(4:0..14): [0 .. 32768),
Read2(4:15..15): BOOLEAN,
fill5(5:0..14): [0 .. 32768),
Write2(5:15..15): BOOLEAN,
fill6(6:0..14): [0 .. 32768),
Read3(6:15..15): BOOLEAN,
fill7(7:0..14): [0 .. 32768),
Write3(7:15..15): BOOLEAN,
fill8(8:0..14): [0 .. 32768),
bitLines(8:15..15): BOOLEAN];
MemoryStateRef: TYPE = REF MemoryStateRec;
MemoryStateRec: TYPE = RECORD [
words: ARRAY [0 .. WordCount) OF Word,
lastRead: ARRAY [0 .. WordCount) OF BOOL
];
CreateMemoryIO: IOCreator = {
cell.realCellStuff.switchIO ← NEW [MemoryIORec];
cell.realCellStuff.newIO ← NEW [MemoryIORec];
cell.realCellStuff.oldIO ← NEW [MemoryIORec];
};
InitializeMemory: Initializer = {
IF leafily THEN
BEGIN
ioRec: MemoryIORef ← NARROW[cell.realCellStuff.newIO];
state: MemoryStateRef ← NEW [MemoryStateRec];
cell.realCellStuff.state ← state;
BEGIN OPEN ioRec, state;
FOR word: CARDINAL IN [0 .. WordCount) DO lastRead[word] ← FALSE ENDLOOP;
END;
END;
};
MemoryValsChanged: CellProc =
BEGIN
sw: MemoryIORef ← NARROW[cell.realCellStuff.switchIO];
newIO: MemoryIORef ← NARROW[cell.realCellStuff.newIO];
state: MemoryStateRef ← NARROW[cell.realCellStuff.state];
BEGIN OPEN sw, state;
TRUSTED {
wordLines: WordLines ← LOOPHOLE[cell.realCellStuff.newIOAsWP];
FOR word: CARDINAL IN [0 .. WordCount) DO
IF wordLines[word].write THEN FOR bit: CARDINAL IN [0 .. WordSize) DO
words[word][bit] ← bitLines[bit].val = H;
ENDLOOP;
ENDLOOP}
END;
END;
MemoryPropQ: CellProc =
BEGIN
sw: MemoryIORef ← NARROW[cell.realCellStuff.switchIO];
newIO: MemoryIORef ← NARROW[cell.realCellStuff.newIO];
state: MemoryStateRef ← NARROW[cell.realCellStuff.state];
BEGIN OPEN sw, state;
TRUSTED {
wordLines: WordLines ← LOOPHOLE[cell.realCellStuff.newIOAsWP];
FOR word: CARDINAL IN [0 .. WordCount) DO
IF wordLines[word].read THEN FOR bit: CARDINAL IN [0 .. WordSize) DO
IF words[word][bit] THEN bitLines[bit].s[q] ← drive;
ENDLOOP;
ENDLOOP}
END;
END;
MemoryPropUD: CellProc =
BEGIN
sw: MemoryIORef ← NARROW[cell.realCellStuff.switchIO];
newIO: MemoryIORef ← NARROW[cell.realCellStuff.newIO];
state: MemoryStateRef ← NARROW[cell.realCellStuff.state];
BEGIN OPEN sw, state;
TRUSTED {
wordLines: WordLines ← LOOPHOLE[cell.realCellStuff.newIOAsWP];
FOR word: CARDINAL IN [0 .. WordCount) DO
IF wordLines[word].read THEN FOR bit: CARDINAL IN [0 .. WordSize) DO
IF words[word][bit] THEN bitLines[bit].s[d] ← drive;
ENDLOOP;
ENDLOOP}
END;
END;
MemoryEvalSimple: CellProc =
BEGIN
sw: MemoryIORef ← NARROW[cell.realCellStuff.switchIO];
newIO: MemoryIORef ← NARROW[cell.realCellStuff.newIO];
state: MemoryStateRef ← NARROW[cell.realCellStuff.state];
BEGIN OPEN newIO, state;
TRUSTED {
wordLines: WordLines ← LOOPHOLE[cell.realCellStuff.newIOAsWP];
readdif: BOOLEAN ← FALSE;
FOR word: CARDINAL IN [0 .. WordCount) DO
IF wordLines[word].write
THEN FOR bit: CARDINAL IN [0 .. WordSize) DO
words[word][bit] ← sw.bitLines[bit].val = H;
ENDLOOP;
readdif ← readdif OR wordLines[word].read # lastRead[word];
lastRead[word] ← wordLines[word].read;
ENDLOOP;
IF readdif THEN PerturbPort[cell, MemoryBitLinesPortIndex];
--THEN FOR bit: CARDINAL IN [0 .. WordSize) DO
--PerturbPort[cell, 2*WordCount + bit];
--ENDLOOP
}
END;
END;
MemoryPorts: Ports ← NEW [PortsRep[9]];
CreateDriverPorts: PROC = {DriverPorts ← RoseCreate.PortsFromFile["MemoryExample.Driver.rosePorts"]};
DriverIORef: TYPE = REF DriverIORec;
DriverIORec: TYPE = MACHINE DEPENDENT RECORD [
bitLines(0:0..63): PACKED ARRAY [0 .. 3] OF SwitchTypes.SwitchVal,
fill1(4:0..11): [0..4095],
asInt(4:12..15): [0..15],
fill2(5:0..14): [0..32767],
drive(5:15..15): BOOLEAN];
-- port indices:
DriverBitLinesPortIndex: CARDINAL = 0;
DriverDrive: TYPE = MACHINE DEPENDENT RECORD [
fill0(0:0..14): [0 .. 32768),
bitLines(0:15..15): BOOLEAN,
fill1(1:0..14): [0 .. 32768),
asInt(1:15..15): BOOLEAN,
fill2(2:0..14): [0 .. 32768),
drive(2:15..15): BOOLEAN];
DriverStateRef: TYPE = REF DriverStateRec;
DriverStateRec: TYPE = RECORD [
wasDriven: BOOL ← FALSE,
lastDriven: [0 .. 16) ← 0
];
CreateDriverIO: IOCreator = {
cell.realCellStuff.switchIO ← NEW [DriverIORec];
cell.realCellStuff.newIO ← NEW [DriverIORec];
cell.realCellStuff.oldIO ← NEW [DriverIORec];
};
InitializeDriver: Initializer = {
IF leafily THEN
BEGIN
state: DriverStateRef ← NEW [DriverStateRec ← []];
cell.realCellStuff.state ← state;
END;
};
DriverPropQ: CellProc =
BEGIN
sw: DriverIORef ← NARROW[cell.realCellStuff.switchIO];
newIO: DriverIORef ← NARROW[cell.realCellStuff.newIO];
state: DriverStateRef ← NARROW[cell.realCellStuff.state];
BEGIN OPEN sw, state;
IF newIO.drive THEN FOR bit: CARDINAL IN [0 .. WordSize) DO
bitLines[bit].s[q] ← drive;
ENDLOOP
END;
END;
DriverPropUD: CellProc =
BEGIN
sw: DriverIORef ← NARROW[cell.realCellStuff.switchIO];
newIO: DriverIORef ← NARROW[cell.realCellStuff.newIO];
state: DriverStateRef ← NARROW[cell.realCellStuff.state];
BEGIN OPEN sw, state;
IF newIO.drive THEN FOR bit: CARDINAL IN [0 .. WordSize) DO
IF BitOps.EBFW[newIO.asInt, 4, bit]
THEN bitLines[bit].s[u] ← drive
ELSE bitLines[bit].s[d] ← drive
ENDLOOP
END;
END;
DriverEvalSimple: CellProc =
BEGIN
sw: DriverIORef ← NARROW[cell.realCellStuff.switchIO];
newIO: DriverIORef ← NARROW[cell.realCellStuff.newIO];
state: DriverStateRef ← NARROW[cell.realCellStuff.state];
BEGIN OPEN newIO, state;
IF drive # wasDriven OR (drive AND asInt # lastDriven) THEN {
--FOR bit: CARDINAL IN [0 .. WordSize) DO PerturbPort[cell, bit] ENDLOOP;
PerturbPort[cell, DriverBitLinesPortIndex];
wasDriven ← drive;
lastDriven ← asInt}
END;
END;
DriverPorts: Ports ← NEW [PortsRep[3]];
MemoryExampleExpand: ExpandProc = {
asInt: Node ← RoseCreate.CreateNode[within: thisCell, name: "asInt", type: NumTypes.NumType[4]];
drive: Node ← RoseCreate.CreateNode[within: thisCell, name: "drive", type: NumTypes.boolType, initialValue: "TRUE"];
bitLines: Node ← RoseCreate.CreateNode[within: thisCell, name: "bitLines", type: SwitchTypes.Bundle[4]];
Read0: Node ← RoseCreate.CreateNode[within: thisCell, name: "Read0", type: NumTypes.boolType];
Write0: Node ← RoseCreate.CreateNode[within: thisCell, name: "Write0", type: NumTypes.boolType];
Read1: Node ← RoseCreate.CreateNode[within: thisCell, name: "Read1", type: NumTypes.boolType];
Write1: Node ← RoseCreate.CreateNode[within: thisCell, name: "Write1", type: NumTypes.boolType];
Read2: Node ← RoseCreate.CreateNode[within: thisCell, name: "Read2", type: NumTypes.boolType];
Write2: Node ← RoseCreate.CreateNode[within: thisCell, name: "Write2", type: NumTypes.boolType];
Read3: Node ← RoseCreate.CreateNode[within: thisCell, name: "Read3", type: NumTypes.boolType];
Write3: Node ← RoseCreate.CreateNode[within: thisCell, name: "Write3", type: NumTypes.boolType];
[] ← RoseCreate.CreateCell[within: thisCell, instanceName: "driver", className: "Driver", interfaceNodes: ""];
[] ← RoseCreate.CreateCell[within: thisCell, instanceName: "memory", className: "Memory", interfaceNodes: ""];
};
MemoryExamplePorts: Ports ← NEW [PortsRep[0]];
RegisterCells[];
END.