Behaviour Registration
BindCellType:
PROC [cellType: Core.CellType, roseClassName:
ROPE]
RETURNS [sameCellType: Core.CellType];
BindCellClass:
PROC [cellClass: Core.CellClass, roseClassName:
ROPE]
RETURNS [sameCellClass: Core.CellClass];
Register:
PROC [roseClassName:
ROPE, init: InitProc ←
NIL, evalSimple: EvalProc ←
NIL, scheduleIfClockEval:
BOOL ←
FALSE]
RETURNS [sameRoseClassName:
ROPE];
InitProc:
TYPE =
PROC [cellType: Core.CellType, flatCellType: CoreFlat.FlatCellType, oldStateAny:
REF
ANY ←
NIL]
RETURNS [stateAny:
REF
ANY ←
NIL, stateValue: LevelSequence ←
NIL];
Initializes the state and the value from the context contained in the cell type. Multiple calls must return different copies of any bits in the state record which actually represent the state of the simulation. If oldStateAny is not NIL then the procedure should reset the state to its initial value rather than allocating new state. stateValue contains a representation of the state value. It is not required. The InitProc and EvalProc own stateValue, Rosemary guarantees not to change it. The size of stateValue, when specified, must be constant across calls to InitProc and EvalProc.
EvalProc:
TYPE =
PROC [stateAny:
REF
ANY, clockEval:
BOOL]
RETURNS [stateValue: LevelSequence ←
NIL];
Must be idempotent. clockEval indicates that only ports combinatorially derived from a clock should be changed, i.e. no state should be updated during such an evaluation. stateValue is the same as in InitProc.
Instantiation
All of the procedures in this section which take Core.Wire arguments may only be called with atomic, canonical (in the CoreFlat sense) wires.
SetFixedWire:
PROC [wire: Core.Wire, level: Level ← L]
RETURNS [sameWire: Core.Wire];
Sets the value of the wire and indicates that the value of the wire may not be changed by Rosemary. This is only intended to be used for atomic public wires of the root cell type such as Vdd and Gnd. These wires partition the network into disjoint blocks connected through transistor gates. It is not a general purpose mechanism for jamming a value onto a wire.
SetWireSize:
PROC [wire: Core.Wire, size: WireSize ← charge]
RETURNS [sameWire: Core.Wire];
WireSize:
TYPE = Drive[chargeWeak..chargeStrong];
SetWireLevel: PROC [wire: Core.Wire, level: Level ← X] RETURNS [sameWire: Core.Wire];
SetWireMemory:
PROC [wire: Core.Wire, memory:
BOOL ←
FALSE]
RETURNS [sameWire: Core.Wire];
If memory is false then the wire is set to X whenever the wire is not driven and the memory boolean in the Settle call is false.
SetTransistorCellTypeSize:
PROC [transistor: Core.CellType, size: TransistorSize]
RETURNS [sameTransistor: Core.CellType];
Sets the order of magnitude transistor size.
SetTransistorInstanceSize:
PROC [transistor: CoreClasses.CellInstance, size: TransistorSize]
RETURNS [sameTransistor: CoreClasses.CellInstance];
TransistorSize:
TYPE = Drive[driveWeak..driveStrong];
Instantiate:
PROC [cellType: Core.CellType, cutSet: CoreFlat.CutSet ←
NIL]
RETURNS [simulation: RoseSimulation];
Flattens the given cell type using the cutSet to determine the leaves of the simulation.
Data Structures
Level: TYPE = {L, H, X};
LevelSequence: TYPE = REF LevelSequenceRec;
LevelSequenceRec:
TYPE =
RECORD [
s: PACKED SEQUENCE size: NAT OF Level];
Drive:
TYPE = {
inspect, -- allows test port to receive value
expect, -- allows test port to specify expected value
none,
--in a test port it means neither driven nor checked; in an eval port it means no strength at all
chargeWeak, chargeMediumWeak,
charge,
chargeMediumStrong, chargeStrong,
force,
-- weakest drive level, allows test procs to check if device has tristated
driveWeak, driveMediumWeak,
drive,
driveMediumStrong, driveStrong,
infinite -- drive for nodes which have infinite current sources
};
DriveSequence: TYPE = REF DriveSequenceRec;
DriveSequenceRec:
TYPE =
RECORD [
s: PACKED SEQUENCE size: NAT OF Drive];
RoseSimulation: TYPE = REF RoseSimulationRec;
RoseSimulationRec:
PUBLIC
TYPE =
RECORD [
cellType: Core.CellType ← NIL,
coreToRoseWires: RefTab.Ref ← NIL,
coreToRoseInstances: RefTab.Ref ← NIL,
instanceNeedEval: RoseCellInstance ← NIL,
instanceNeedEvalWhenNotClockEval: RoseCellInstance ← NIL,
perturbed: RoseWire ← NIL,
vicinityByStrength: ARRAY Drive OF VicinityRec,
time: INT ← 0];
VicinityRec:
TYPE =
RECORD[
wires: RoseWires,
firstFree: CARDINAL ← 0];
RoseCellType: TYPE = REF RoseCellTypeRec;
RoseCellTypeRec:
TYPE =
RECORD [
init: InitProc ← NIL,
evalSimple: EvalProc ← NIL,
scheduleIfClockEval: BOOL ← FALSE];
RoseCellInstances: TYPE = LIST OF RoseCellInstance;
RoseCellInstance: TYPE = REF RoseCellInstanceRec;
RoseCellInstanceRec:
TYPE =
RECORD [
nextNeedEval: RoseCellInstance ← NIL,
nextNeedEvalWhenNotClockEval: RoseCellInstance ← NIL,
roseCellType: RoseCellType ← NIL,
state: REF ANY ← NIL,
log: RoseLog ← NIL,
flatCellType: CoreFlat.FlatCellTypeRec];
RoseWireList: TYPE = LIST OF RoseWire;
RoseWires: TYPE = REF RoseWireSeq;
RoseWireSeq: TYPE = RECORD [s: SEQUENCE size: CARDINAL OF RoseWire];
RoseWire: TYPE = REF RoseWireRec;
RoseWireRec:
TYPE =
RECORD [
ports: RosePorts ← NIL,
nextPerturbedWire: RoseWire ← NIL,
previousPerturbedWire: RoseWire ← NIL,
nextRecomputed: RoseWire ← NIL,
nextVicinityWire: RoseWire ← NIL,
channels: RoseTransistors ← NIL,
notOffChannels: RoseTransistors ← NIL,
validNotOffChannels: CARDINAL ← 0,
gates: RoseTransistors ← NIL,
switchDrive: Drive ← none,
upDrive: Drive ← none,
downDrive: Drive ← none,
wireDrive: Drive ← charge,
wireValue: Level ← L,
mark: BOOL ← FALSE,
memory: BOOL ← FALSE,
log: RoseLog ← NIL,
flatWire: CoreFlat.FlatWireRec];
RoseTransistors: TYPE = REF RoseTransistorSeq;
RoseTransistorSeq: TYPE = RECORD [s: SEQUENCE size: CARDINAL OF RoseTransistor];
RoseTransistor: TYPE = REF RoseTransistorRec;
RoseTransistorRec:
TYPE =
RECORD [
gate: RoseWire ← NIL,
ch1: RoseWire ← NIL,
ch2: RoseWire ← NIL,
conductivity: Drive ← drive,
transistorType: CoreClasses.TransistorType ← nE,
flatCellType: CoreFlat.FlatCellTypeRec];
RosePorts: TYPE = REF RosePortSeq;
RosePortSeq: TYPE = RECORD [s: SEQUENCE size: CARDINAL OF RosePort];
RosePort: TYPE = REF RosePortRec;
RosePortRec:
TYPE =
RECORD [
instance: RoseCellInstance ← NIL,
level: Level ← X,
drive: Drive ← none,
wire: RoseWire ← NIL];
The plan is to write all the data for all of the wires and cells on the remote disk. All of the data for each wire or cell that is currently plotted is also stored in the VM of the local machine. The remote machine knows which wires are currently plotted and calls the local machine with any updates.
RoseLog: TYPE = REF RoseLogRec;
RoseLogRec:
TYPE =
RECORD [
lastFilePos: INT ← -1, -- the file position of the last sample written
list: RoseSampleList ← NIL, -- if non-nil, the samples for this object are currently kept in memory
previous: RoseSample ← NIL, -- the previous sample
currentTime: INT ← -1, -- time of current sample
current: RoseSample ← NIL]; -- the sample currently taken, not guaranteed if time=lastUpdateTime ???? what is time and lastUpdateTime RB
The following assertions must hold:
- current.next = NIL
- current.time = value of time at last call to Update
- current will never be modified once time of Update call > current.time
- previous is the sample that was valid just before current. It is necessary to allow collapsing current with a previous value. previous has not yet been written to disk!
- if previous#NIL, then previous.next=current
- if list#NIL, then samples are kept in memory. Then, either list.head=previous=NIL, or previous may be reached by following next links from list.head (possibly 0 times!).
RoseSampleList: TYPE = REF RoseSampleListRec;
RoseSampleListRec:
TYPE ~
RECORD [
head: RoseSample, -- the head of the list. The tail is always LogData.current
beforeHeadPos: INT, -- the file position of the predecessor of head, <0 => no predecessor
inTable: BOOL ← FALSE]; -- used internally to RBT management, don't modify
The in-memory representation of a list of samples. The samples back in time may still be on disk, starting at beforeHeadPos. SampleLists are created only when necessary.
RoseSample: TYPE = REF RoseSampleRec;
RoseSampleRec:
TYPE =
RECORD [
next: RoseSample ← NIL,
time: INT ← LAST[INT], -- time at which this event occured
value: PACKED SEQUENCE size: CARDINAL OF Level];
The object has the specified value in the range [sample.time..sample.next.time)