<> <<>> <<>> DIRECTORY BitOps, Core, CoreClasses, CoreCreate, CoreProperties, Ports, Rosemary, RosemaryUser, TamPorts, TamEu, Rope, TamDefs, TamPc; RegFileCells: CEDAR PROGRAM IMPORTS Ports, Rosemary, TamPorts, TamEu, TamPc = BEGIN OPEN TamDefs, TamPorts; BoolToInt: PROC [b: BOOL] RETURNS [NAT] = {RETURN[IF b THEN 1 ELSE 0]}; busBits: NAT _ 32; <<-------------------- Register File --------------------->> banks: NAT = 6; bankSize: NAT = 40; RegisterFileState: TYPE = REF RegisterFileStateRec; RegisterFileStateRec: TYPE = RECORD [ d1, d2, r, writeOk, writeOctal, dSwap, memtoD1, memtoD2, state, nextRAddr, clock2, vdd, gnd: NAT _ LAST[NAT], lastClock, curState: NAT, curAddr: ARRAY [0..1] OF NAT]; registerArray: ARRAY [0..576) OF Word; RegisterFileInit: Rosemary.InitProc = { <<>> <<--PROC [cellType: Core.CellType, p: Ports.Port] RETURNS [stateAny: REF ANY _ NIL]-->> state: RegisterFileState _ NEW[RegisterFileStateRec]; [] _ Ports.InitPorts[cellType, l, none, "Vdd", "Gnd", "Clock2"]; [] _ Ports.InitPorts[cellType, ls, none, "R", "WriteOk", "WriteOctal", "DSwap", "MemtoD1", "MemtoD2", "State", "NextRAddr"]; [] _ Ports.InitPorts[cellType, ls, drive, "D1", "D2"]; [state.vdd, state.gnd, state.clock2] _ Ports.PortIndexes[cellType.public, "Vdd", "Gnd", "Clock2"]; [state.r, state.writeOk, state.writeOctal, state.dSwap, state.memtoD1, state.memtoD2, state.state, state.nextRAddr] _ Ports.PortIndexes[cellType.public, "R", "WriteOk", "WriteOctal", "DSwap", "MemtoD1", "MemtoD2", "State", "NextRAddr"]; [state.d1, state.d2] _ Ports.PortIndexes[cellType.public, "D1", "D2"]; FOR i: NAT IN [0..576) DO registerArray[i] _ ZerosWord; ENDLOOP; state.lastClock _ 0; state.curAddr _ [0, 0]; state.curState _ 0; [] _ Rosemary.SetFixedWire[cellType.public[state.vdd], H]; [] _ Rosemary.SetFixedWire[cellType.public[state.gnd], L]; stateAny _ state; }; RegisterFileEvalSimple: Rosemary.EvalProc = { <> state: RegisterFileState _ NARROW[stateAny]; D1, D2: Word; xS: BOOL _ HasXs[p, state.writeOk] OR HasXs[p, state.writeOctal] OR HasXs[p, state.dSwap] OR HasXs[p, state.state] OR HasXs[p, state.nextRAddr]; ClrP[p, state.d1]; ClrP[p, state.d2]; IF NOT xS THEN { IF (PortToNat[p, state.clock2] = 1) AND (state.lastClock = 0) THEN { state.curAddr[state.curState] _ PortToNat[p, state.nextRAddr]; state.curState _ PortToNat[p, state.state]; }; D1 _ registerArray[state.curAddr[0]]; D2 _ registerArray[state.curAddr[0]-1]; IF PortToBool[p, state.dSwap] THEN {temp: Word _ D1; D1 _ D2; D2 _ temp;}; IF PortToBool[p, state.memtoD1] THEN SetPWord[p, state.d1, D1]; IF PortToBool[p, state.memtoD2] THEN SetPWord[p, state.d1, D2]; IF (state.curState = 1) AND PortToBool[p, state.writeOk] THEN registerArray[state.curAddr[1]] _ PortToTamWord[p, state.r]; }; stateAny _ state; }; <<>> <<-------------------- RegFile6TRamCell --------------------->> RegFile6TRamCellState: TYPE = REF RegFile6TRamCellStateRec; RegFile6TRamCellStateRec: TYPE = RECORD [in, nIn, selWrite, out, vdd, gnd: NAT _ LAST[NAT], storedval: NAT]; RegFile6TRamCellInit: Rosemary.InitProc = { <<>> <<--PROC [cellType: Core.CellType, p: Ports.Port] RETURNS [stateAny: REF ANY _ NIL]-->> state: RegFile6TRamCellState _ NEW[RegFile6TRamCellStateRec]; [] _ Ports.InitPorts[cellType, l, none, "Vdd", "Gnd"]; [] _ Ports.InitPorts[cellType, ls, none, "In", "nIn", "SelWrite"]; [] _ Ports.InitPorts[cellType, ls, drive, "Out",]; [state.vdd, state.gnd] _ Ports.PortIndexes[cellType.public, "Vdd", "Gnd"]; [state.in, state.nIn, state.selWrite, state.out] _ Ports.PortIndexes[cellType.public, "In", "nIn", "SelWrite", "Out"]; state.storedval _ 0; [] _ Rosemary.SetFixedWire[cellType.public[state.vdd], H]; [] _ Rosemary.SetFixedWire[cellType.public[state.gnd], L]; stateAny _ state; }; RegFile6TRamCellEvalSimple: Rosemary.EvalProc = { <> state: RegFile6TRamCellState _ NARROW[stateAny]; xS: BOOL _ HasXs[p, state.in] OR HasXs[p, state.nIn] OR HasXs[p, state.selWrite]; IF NOT xS THEN IF PortToNat[p, state.selWrite] = 1 THEN { in: NAT _ PortToNat[p, state.in]; nIn: NAT _ PortToNat[p, state.nIn]; IF (in + nIn) = 1 THEN state.storedval _ in; }; SetP[p, state.out, state.storedval]; p[state.out].d _ drive; stateAny _ state; }; RegFile6TCellName: Rope.ROPE = Rosemary.Register[roseClassName: "RegFile6TRamCell", init: RegFile6TRamCellInit, evalSimple: RegFile6TRamCellEvalSimple]; regFileName: Rope.ROPE = Rosemary.Register[roseClassName: "RegisterFile", init: RegisterFileInit, evalSimple: RegisterFileEvalSimple]; END. <<>>