10-03-2015 07:16 PM
i know how to make generic byte write, word write memory models in verilog for FPGAs. but is there any way of making a bit write memory model?
i have looked online quite a lot but couldn't find one. and the memory model i am making ends up having a couple of cycles of delay in reads and write (because of the bit-write nature). so if someone has worked with bitwrite memory models or knows where to find generic code for them (online link), that would be great.
thanks in advacne for the help.
10-03-2015 08:46 PM
The issue is (probably) not with the Verilog but with the capability of the block RAMs in the FPGA.
The RAMB36 (and other RAMs) have enables per byte (only); each enable controls the writing of 8 (or 9) bits of the RAM. There is no smaller granularity for the block RAM.
If you really need bit write capability, you have two choices:
- use distributed RAM - each RAM is 64x1 bit, so is inherently bit writeable, but the RAMs are small; building large ones will take a lot of resources and will start getting slow as the depth starts getting larger
- implement a read-modify-write outside the block RAM
- each write to the RAM first reads the entire byte/word, modifies the bits you want to change, and writes back the entire byte/word to the RAM
- of course, this requires at least 2, if not 3 clock cycles to do an operation, and either requires that operations not be done every clock, or that you use a dual ported RAM
10-04-2015 06:38 PM
It wouldn't make sense for a small memory like 256 x 12, but a third option is to use the RAMB in 1 bit wide mode, so you would need one RAMB per bit, 12 in all. Depending on the device, this would create a minimum of 8K or 16K deep memory.
As far as inferring this sort of RAM, you may need to experiment in order to make sure that the synthesis tool can understand your code to be a RAM template. It certainly should work to create a generic 1-bit wide RAM as a module and then instantiate 12 of them as an array of intantiations (or in a generate for loop). It's not clear whether the tools would give you what you want by simply coding a per-bit write enable, but it's worth a try. That could be coded in a procedural loop like:
always @ (posedge wr_clk)
for (i = 0;i < WIDTH;i = i + 1) if (wr_ena[i]) RAM[wr_addr][i] <= din[i];
If you're lucky the tools will fit that into distributed RAM for you.