Community
cancel
Showing results for 
Search instead for 
Did you mean: 
PElm
Beginner
1,115 Views

Automatic use of internal block RAMs

I'm translating code from Xilinx devices to Intel to see if we could switch to Altera FPGAs.

Xilinx tools automatically translate VHDL memory operations to block-ram without need to use macros or components.

This make it very simple to have a common code base for different FPGA-families.

 

The following code works for all xilinx devices. The result is 1 block ram.

However when I do this in Quartus the result is a lot of logic. 

 

Can I force it somehow to use block ram or can I write different. I do not want to use megafunctions or device specific component etc if not necessary.

 

 

library ieee; use ieee.std_logic_1164.all; use ieee.std_logic_unsigned.all;   entity MemStd is port ( Clk : in std_logic; Reset : in std_logic; DOA : out std_logic_vector( 8 downto 0); ADDRA : in std_logic_vector(10 downto 0); ADDRB : in std_logic_vector(10 downto 0); DIB : in std_logic_vector( 8 downto 0); WEB : in std_logic ); end entity;   architecture IMPL of MemStd is -- Shared memory type mem_t is array ( 0 to (2**11)-1 ) of std_logic_vector(9-1 downto 0); shared variable mem : mem_t := ( '0'&x"12",'0'&x"12",'0'&x"13",'0'&x"14",'0'&x"55",'0'&x"66 ",'1'&x"77",'1'&x"88", '1'&x"FF",'1'&x"88",'1'&x"12",'1'&x"11",'0'&x"11",'0'&x"00",'0'&x"12",'0'&x"15", '0'&x"12",'0'&x"12",'0'&x"13",'0'&x"14",'0'&x"55",'0'&x"66 ",'1'&x"77",'1'&x"88", '1'&x"FF",'1'&x"88",'1'&x"12",'1'&x"11",'1'&x"11",'1'&x"00",'1'&x"12",'1'&x"15", '0'&x"12",'0'&x"12",'0'&x"13",'0'&x"14",'0'&x"55",'0'&x"66 ",'0'&x"77",'0'&x"88", -- Rest of memory init... ,others=>"000000000"); begin -- Port A Write WRP : process(Clk) begin if rising_edge(Clk) then if(WEB='1') then mem(conv_integer(ADDRB)) := DIB; end if; end if; end process; -- Port B Read process(Clk) begin if rising_edge(Clk) then DOA <= mem(conv_integer(ADDRA)); end if; end process; end IMPL;

 

0 Kudos
8 Replies
Daixiwen
New Contributor I
145 Views

You will find recommended ways of describing memory in hdl in this document: https://www.intel.com/content/www/us/en/programmable/documentation/sbc1513987577203.html#mwh14099595...

If you don't stick to the guide, sometimes it works and sometimes it doesn't. AFAIK shared variables are only used in Quartus to describe memories with dual clocks.

Tricky
New Contributor II
145 Views

Using a shared variable implies write-before-read behaviour. Historically Altera could only infer read-before-write behaviour and if you needed write-before-read it had to be done using an altsyncram with the appropriate generic.

 

It now appears that write-before-read can be infered, but using a variable in a single process, rather than a shared variable over 2 processes.

 

To be safe, Both Xilinx and Altera will always infer a ram using a signal rather than shared variable.

PElm
Beginner
145 Views

@Daixiwen​ @Tricky​ 

I changed to using signals instead and read/write in the same process.

It works fine and one memory is created. However this only works when I'm not initializing the memory content. Then everything becomes logic again.

I don't understand how Altera want me to write the initialization of the memory content in VHDL.

Tricky
New Contributor II
145 Views

Intel should accept initialisation just like Xilinx. What family are you targetting?

Daixiwen
New Contributor I
145 Views

According to the "Specifying Initial Memory Contents at Power-Up

" chapter in the document https://www.intel.com/content/www/us/en/programmable/documentation/sbc1513987577203.html#mwh14099595... , the recommended way to initialize the memory is to give a default value to the signal. Check if there is any sublte difference between your code and the example given by altera that could confuse the synthesizer.

PElm
Beginner
145 Views

@Tricky​ I use Max10

corestar
New Contributor I
145 Views

If you right-click in a VHDL windows, there is an "Insert Template" option that can be useful. There is a ROM example.

 

I've used the memory initialization and it works within limits. The templates use functions.

 

 

Just a side note, for VHDL 2008, instead of:

'1'&x"12"

you could use:

9x"112"   or   9x"1_12"

 

corestar
New Contributor I
145 Views

Dear Intel, some of us are really really trying to use the forums you made a mess of, but I'm awfully tired of hitting "Show More" and "Latest Posts" instead of "Top Posts".

Reply