0
0
VhdlHow-ToBeginner · 4 min read

How to Model RAM in VHDL: Syntax and Example

To model RAM in VHDL, define a memory array using a type and a signal or variable to hold data. Use a process sensitive to clock and control signals to read and write data at specified addresses.
📐

Syntax

Modeling RAM in VHDL involves declaring a memory array type, a signal to hold the memory content, and a process to handle read and write operations synchronized with a clock.

  • type: Defines the memory array type (e.g., array of std_logic_vector).
  • signal: Holds the actual memory content.
  • process: Controls reading and writing based on clock and enable signals.
  • address: Selects the memory location.
  • data_in and data_out: Input and output data buses.
vhdl
type ram_type is array (0 to 15) of std_logic_vector(7 downto 0);
signal ram : ram_type := (others => (others => '0'));

process(clk)
begin
  if rising_edge(clk) then
    if write_enable = '1' then
      ram(to_integer(unsigned(address))) <= data_in;
    end if;
    data_out <= ram(to_integer(unsigned(address)));
  end if;
end process;
💻

Example

This example shows a simple 16x8 RAM model with synchronous write and asynchronous read. It writes data to the RAM on the rising clock edge when write_enable is high and outputs the data at the given address.

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

entity ram_model is
  port(
    clk         : in std_logic;
    write_enable: in std_logic;
    address     : in std_logic_vector(3 downto 0);
    data_in     : in std_logic_vector(7 downto 0);
    data_out    : out std_logic_vector(7 downto 0)
  );
end ram_model;

architecture behavioral of ram_model is
  type ram_type is array (0 to 15) of std_logic_vector(7 downto 0);
  signal ram : ram_type := (others => (others => '0'));
begin
  process(clk)
  begin
    if rising_edge(clk) then
      if write_enable = '1' then
        ram(to_integer(unsigned(address))) <= data_in;
      end if;
    end if;
  end process;

  data_out <= ram(to_integer(unsigned(address)));
end behavioral;
⚠️

Common Pitfalls

Common mistakes when modeling RAM in VHDL include:

  • Forgetting to convert std_logic_vector address to integer using to_integer(unsigned(address)).
  • Writing data outside the clocked process, causing simulation mismatches.
  • Not initializing the RAM, leading to unknown values.
  • Mixing synchronous and asynchronous read/write incorrectly.

Correct usage ensures writes happen only on clock edges and reads reflect current memory content.

vhdl
-- Wrong: Writing outside clocked process
ram(to_integer(unsigned(address))) <= data_in; -- This causes combinational write

-- Right: Writing inside clocked process
process(clk)
begin
  if rising_edge(clk) then
    if write_enable = '1' then
      ram(to_integer(unsigned(address))) <= data_in;
    end if;
  end if;
end process;
📊

Quick Reference

  • Use type to define RAM size and data width.
  • Use signal to hold RAM content.
  • Use a clocked process for writing data.
  • Convert address from std_logic_vector to integer with to_integer(unsigned(address)).
  • Initialize RAM to avoid unknown values.

Key Takeaways

Model RAM as an array signal with a defined type and size.
Use a clocked process to write data synchronously to RAM.
Convert address signals properly to integer indexes.
Initialize RAM to known values to avoid simulation issues.
Separate read and write logic clearly for correct behavior.