How to write RAM code in VHDL | applied electronics engineering

Latest

How to write RAM code in VHDL

By Applied Electronics - Thursday, January 5, 2017 No Comments
In this VHDL tutorial we explain how to write RAM code in VHDL. When developing digital system you will have to incorporate RAM memory in your system so this will be useful for you.

A RAM memory has some address bits say n to read the memory location. If n is the address bits, then the number of address location you can access is 2^n. Each address location would store data called words. These words also have their own bit length let's say m.

Define the input and output ports for your RAM.

If you recall your undergraduate computer classes(who can remember all the details anyway), the inputs ports to a RAM are clock(1 bit), reset(1 bit), write enable(1 bit), write address(n bits), write data(m bits) and the output port is the read data(m bits).

For simplicity assume that the address bit is 2, that is n = 2 and therefore there are 2^2 = 4 memory location. Also let's assume that the word size of the memory is 8 bits, that is, n = 8.

For example,
[0] 10101010
[1] 00101011
[2] 11001010
[3] 01111001

Assuming this initial condition, lets start by giving some name to the entity, lets say RAM. Let the 4 required input ports name be clk, rst, w_en, w_addr, w_data and output r_data.

Then the entity declaration is,

entity RAM is
port(
clk, rst, w_en : in std_logic;
w_addr, w_data : in std_logic_vector(1 downto 0);
r_data : out std_logic_vector(1 downto 0);
);
end RAM

Defining the Architecture,

So now comes the architecture description of the RAM. The architecture of RAM consist of 3 constituents-
1. array declaration
2. process to reset and write data into the array
3. read data

1. an array declaration
The RAM can be constructed using the Array feature of VHDL. In this some name for the array must be provided let's call it RAM_ARRAY. The array has some number of rows and column. The number of row is the number of memory location which is 2^n as mentioned earlier. With n= 2 this becomes 4 (meaning with 0 included- 0, 1, 2, 3). And the number of column is the word size which is m = 8(with 0 included this becomes 0, 1, 2, 3 .....7). See the above illustration of bits arrangement.

Now lets define this array,

type RAM_ARRAY is array(3 downto 0) of std_logic_vector(7 downto 0)

2. a process to read, write, reset the array

The logic involved in reading and writing into the RAM is as follows,

1. if the reset is high( bit 1) then the memory should be cleared.
if (rst = '1') then mem <= "00000000";
2. if the write enable is high then the data from the write data port should be placed into the memory
if w_en = '1' then mem(to_integer(unsigned(w_addr))) <= w_data;
3. The 2nd logic above should be valid during the clocking process
4.  The data can be read from the memory using the read address port.
r_data <= mem(to_integer(unsigned(r_addr)));

The code for the above logic is,

process(clk, rst)
begin
if(rst = '1')then mem <= (others=>(others => '0'));
elsif(clk'event and clk = '1')then
if w_en = '1' then
mem(to_integer(unsigned(w_addr))) <= w_data;
end if;
end if;
end process;

r_data <= mem(to_integer(unsigned(r_addr)));

And the overall architecture body is,

architecture RAM_arch of RAM is

type RAM_ARRAY is array(3 downto 0) of std_logic_vector(7 downto 0);

signal mem : RAM_ARRAY;

begin
process(clk, rst)
begin
if(rst = '1')then mem <= (others=>(others => '0'));
elsif(clk'event and clk = '1')then
if w_en = '1' then
mem(to_integer(unsigned(w_addr))) <= w_data;
end if;
end if;
end process;

r_data <= mem(to_integer(unsigned(r_addr)));

end RAM_arch;

The Code of the overall RAM is,

library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;

entity RAM is
 port(
 clk, rst, w_en : in std_logic;
 w_addr, r_addr : in std_logic_vector(1 downto 0);
 w_data : in std_logic_vector(7 downto 0);
 r_data : out std_logic_vector(7 downto 0)
 );
end RAM;  
architecture RAM_arch of RAM is

type RAM_ARRAY is array(3 downto 0) of std_logic_vector(7 downto 0);
signal mem : RAM_ARRAY;

begin
 process(clk, rst)
 begin
  if(rst = '1')then mem <= (others=>(others => '0'));
  elsif(clk'event and clk = '1')then
   if w_en = '1' then
    mem(to_integer(unsigned(w_addr))) <= w_data;
   end if;
  end if;
  end process;
 
  r_data <= mem(to_integer(unsigned(r_addr)));

end RAM_arch;


See FPGA design tutorial page

Tags:

No Comment to " How to write RAM code in VHDL "