X-Git-Url: http://git.megacz.com/?a=blobdiff_plain;f=ships%2FMemory.ship;h=2d1d6f15dbe6abc7fe5b7e02c51d47ebcdfdf943;hb=aee85d3dd0435554e14e03b97f268752843a441f;hp=c8cd957089baf05347526dbb726fc70d74d11d55;hpb=7bbbd4be446d1426a2cbc34e61dfb42a6f7cfcaa;p=fleet.git diff --git a/ships/Memory.ship b/ships/Memory.ship index c8cd957..2d1d6f1 100644 --- a/ships/Memory.ship +++ b/ships/Memory.ship @@ -2,19 +2,101 @@ ship: Memory == Ports =========================================================== data in: inCBD -data in: inAddr.read -data in: inAddr.write -data in: inAddr.readMany -data in: inAddr.writeMany -data in: inData -data in: inStride -data in: inCount +data in: inAddrRead +data in: inAddrWrite +data in: inDataWrite data out: out +== TeX ============================================================== + +The {\tt Memory} ship represents an interface to a storage space, +which can be used to read from it or write to it. This storage space +might be a fast on-chip cache, off chip DRAM, or perhaps even a disk +drive. + +Generally, distinct {\tt Memory} ships do not access the same backing +storage, although this is not strictly prohibited. + +Each {\tt Memory} ship may have multiple {\it interfaces}, numbered +starting with {\tt 0}. Each interface may have any subset of the +following docks: {\tt inCBD}, {\tt inAddrRead}, {\tt inAddrWrite}, +{\tt inDataWrite}, and {\tt out}. If {\tt inCBD} or {\tt inAddrRead} +is present on an interface, then {\tt out} must be present as well. +If {\tt inAddrWrite} is present then {\tt inDataWrite} must be present +as well. + +Each interface serializes the operations presented to it; this means +that an interface with both read and write capabilities will not be +able to read and write concurrently. Instead, a {\tt Memory} ship +with the ability to read and write concurrently should have two +interfaces, one which is read-only and one which is write-only. + +There may be multiple {\tt Memory} ships which interface to the same +physical storage space. An implementation of Fleet must provide +additional documentation to the programmer indicating which {\tt +Memory} ships correspond to which storage spaces. A single {\tt +Memory} ship may also access a ``virtual storage space'' formed by +concatenating multiple physical storage spaces. + +\subsection*{Code Bag Fetch} + +When a word appears at the {\tt inCBD} port, it is treated as a {\it +code bag descriptor}, as shown below: + +\begin{center} +\setlength{\bitwidth}{3mm} +{\tt +\begin{bytefield}{37} + \bitheader[b]{36,6,5,0}\\ + \bitbox{31}{Address} + \bitbox{6}{size} +\end{bytefield} +} +\end{center} + +When a word arrives at the {\tt inCBD} port, it is treated as a memory +read with {\tt inAddrRead=Address}, {\tt inStride=1}, and {\tt +inCount=size}. + +\subsection*{Reading} + +When a word is delivered to {\tt inAddrRead}, the word residing in +memory at that address is provided at {\tt out}. The {\tt c-flag} at +the {\tt out} port is set to zero. + +\subsection*{Writing} + +When a word is delivered to {\tt inAddrWrite} and {\tt inDataWrite}, +the word at {\tt inDataWrite} is written to the address specified by +{\tt inAddrWrite}. Once the word is successfully committed to memory, +the value {\tt inAddr+inStride} is provided at {\tt out} (that is, the +address of the next word to be written). The {\tt c-flag} at +the {\tt out} port is set to one. + +\subsection*{To Do} + +Stride and count are not implemented. + +We need a way to do an ``unordered fetch'' -- a way to tell the memory +unit to retrieve some block of words in any order it likes. This can +considerably accelerate fetches when the first word of the region is +not cached, but other parts are cached. This can also be used for +dispatching codebags efficiently -- but how will we make sure that +instructions destined for a given pump are dispatched in the correct +order (source sequence guarantee)? + +A more advanced form would be ``unordered fetch of ordered records'' +-- the ability to specify a record size (in words), the offset of the +first record, and the number of records to be fetched. The memory +unit would then fetch the records in any order it likes, but would be +sure to return the words comprising a record in the order in which +they appear in memory. This feature could be used to solve the source +sequence guarantee problem mentioned in the previous paragraph. + == Fleeterpreter ==================================================== private long[] mem = new long[0]; - public long readMem(int addr) { return mem[addr]; } + public long readMem(int addr) { return addr >= mem.length ? 0 : mem[addr]; } public void writeMem(int addr, long val) { if (addr >= mem.length) { long[] newmem = new long[addr * 2 + 1]; @@ -23,144 +105,144 @@ data out: out } mem[addr] = val; } - - public void dispatch(int addr, int size) { - for(int i=addr; i> 6); - base = base & ~(0xffffffff << 18); - int size = (int)launch; - size = size & ~(0xffffffff << 6); - dispatch(base, size); + private Queue toDispatch = new LinkedList(); + public void reset() { + super.reset(); + mem = new long[0]; + toDispatch.clear(); } - public void service() { + if (toDispatch.size() > 0) { + if (!box_out.readyForDataFromShip()) return; + box_out.addDataFromShip(toDispatch.remove()); + } if (box_inCBD.dataReadyForShip()) { long val = box_inCBD.removeDataForShip(); - long addr = val >> 6; - long size = val & 0x3f; - dispatch((int)addr, (int)size); - } - if (box_inAddr.dataReadyForShip() && box_out.readyForItemFromShip()) { - Packet packet = box_inAddr.peekPacketForShip(); - if (packet.destination.getDestinationName().equals("read")) { - box_out.addDataFromShip(readMem((int)box_inAddr.removeDataForShip())); - } else if (packet.destination.getDestinationName().equals("write") && box_inData.dataReadyForShip()) { - writeMem((int)box_inAddr.removeDataForShip(), - box_inData.removeDataForShip()); - box_out.addDataFromShip(0); - } + long addr = ((Interpreter)getFleet()).CBD_OFFSET.getval(val); + long size = ((Interpreter)getFleet()).CBD_SIZE.getval(val); + for(int i=0; i