I would like to code the on-chip memory in vendor neutral VHDL. I got it running for a dual-port memory with single clock and same port sizes for the read and write port.
However, I need a memory with a 32-bit write port and an 8-bit read port. So far I was not able to code it in VHDL in a way that the Synthesizer inferres the correct block ram without an extra read MUX.
BTW: I do my test at the moment with Quartus. Will see how Xilinx XSE will support this.
I'll give up one this vendor independent block RAM project. For the 32-bit write data, 8-bit read data with registered address, in data and unregistered out data RAM coded in VHDL I got:
On the Altera Cyclone: generates a 32-bit dual port RAM with an external 4:1 MUX. This MUX hurts fmax (from 94MHz down to 84MHz)!
On the Xlinix Spartan-3: The RAM gets implemented as distributed RAM! Uses a lot of LCs and the fmax goes from 65MHz down to
50MHz
So I will bite the bullet and use two vendor specific VHDL files. However, there is one open issue: I want the memory size be configurable via a generic. This is possible with Alteras altsyncram.
For Xilinx I only know those RAMB16_S9_S36 components where the memory size is part of the component name. Is there a a Xilinx block RAM component where I can specify the size?
The RAMB16 elements are the raw RAM macros. The Sx part of the name indicates the port width. You can build up bigger memories in Coregen which is a bit like the Altera Megawizard tool or build them up yourself using generic statements using the raw macros.
If you looking at switching between vendors one trick is to hide a RAM inside a wrapper file. If you use the wrapper level as the RAM component for instantiation then you will only have to change the technology based memory element in one place i.e. the the wrapper file.
Some synthesisers are capable of inferring RAM usually using an indexed array of something like VHDL's "std_logic_vector". I can't tell you much about the results as it isn't my own preferred method but a non-vendor synthesiser may do better than one offered by the silicon vendors.
John Adair Enterpoint Ltd. - Home of FPGA PCI Development Boards.
the port width. You can build up bigger memories in
yourself using generic statements using the raw macros.
Can you describe this a little bit more specific, please? Are the other components available to describe Xilinx block RAMs?
BTW: With the web edition I don't have Coregen and I also don't use the Megawizzard in Quartus. Ideal setup is a single generic parameter with the memory size (in lenght of the address).
a wrapper file. If you use the wrapper level as the
technology based memory element in one place i.e. the the
That's the way I do it. I switch between technologies with different files in the project. I also use this different VHDL files in projects for other customization - primitiv, but efficient.
of something like VHDL's "std_logic_vector". I can't
non-vendor synthesiser may do better than one offered by
The Xilinx tool interffered distributed RAM from the VHDL description. A thing I definitely don't want. Quartus had problems with the different port sizes, but single port sizes work very well.
type ram_t is array(BIT_DEPTH-1 downto 0) of std_logic_vector(BIT_WIDTH-1 downto 0);
-- infer RAM signal blockram : ram_t;
begin
-- Note, Spartan-II doesn't have "No Change Mode"; -- Using Block RAM Single Port "Write First Mode" process (clk) begin if rising_edge(clk) then if (en = '1') then if (we = '1') then blockram(to_integer(unsigned(AB)))
Not so bad! The infering architecture generates a block ram for the Spartan-3. However, with Quartus it generates registers. A little step forward ;-)
The next step is to generate a memory with different port sizes. The attached code instances a block ram with a MUX in Quartus and distributed memory with the Xilinx tool.
One good place for information is the libraries guide. A version of it is here
formatting link
. The RAMB16 macros are basically the size of a single block ram - 16Kbit (18Kbit with parity). There is also help on ram component instantiation in ISE (I believe this is in Webpack). If you click on the lightbulb icon in the ISE tool you should get to some templates.
I don't think you will find any other size as ready built macro for Xilinx RAM. You will have build that up yourself if you don't have Coregen.
John Adair Enterpoint Ltd. - Home of Broaddown2. The Ultimate Spartan3 Development Board.
There is for Virtex4: the Ramb16 component sets the aspect ratio with generics/attributes. It, however, is not backwards compatible with the earlier families.
You can write a single file that uses generate to select the appropriate BRAM size based on input widths or generics. Once written, it can be used in many projects, so hopefully you can ammortize the coding effort over many projects. Once done, the generates are transparent to the end user unless he decides he has to look under the hood to see what the generic RAM you created has under the hood.
The Virtex 4 "RAMB16" component lets you set the aspect ratio with generics/attributes. But it still only generates a single BlockRAM. If you want a RAM which is larger than 18kbits, then you need to instantiate the RAMB16 component multiple times.
-- Fergus J. Henderson "I have always known that the pursuit Galois Connections, Inc. of excellence is a lethal habit" Phone: +1 503 626 6616 -- the last words of T. S. Garp.
ElectronDepot website is not affiliated with any of the manufacturers or service providers discussed here.
All logos and trade names are the property of their respective owners.