Bird
Raised Fist0
VHDLprogramming~10 mins

ROM using constant array in VHDL - Step-by-Step Execution

Choose your learning style10 modes available
Concept Flow - ROM using constant array
Define constant array with data
↓
Create ROM entity and architecture
↓
On address input change
↓
Read data from constant array at address
↓
Output data on data bus
↓
End
This flow shows how a ROM is created using a constant array in VHDL and how data is read from it based on the input address.
Execution Sample
VHDL
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;

entity ROM is
  port(address : in std_logic_vector(1 downto 0);
       data : out std_logic_vector(3 downto 0));
end ROM;

architecture Behavioral of ROM is
  constant ROM_Array : array(0 to 3) of std_logic_vector(3 downto 0) := (
    "0001", "0010", "0100", "1000"
  );
begin
  process(address) begin
    data <= ROM_Array(to_integer(unsigned(address)));
  end process;
end Behavioral;
This VHDL code defines a ROM with 4 addresses, each storing 4-bit data, and outputs data based on the input address.
Execution Table
StepInput AddressAddress (int)ROM_Array AccessOutput Data
1"00"0ROM_Array(0)"0001"
2"01"1ROM_Array(1)"0010"
3"10"2ROM_Array(2)"0100"
4"11"3ROM_Array(3)"1000"
5Any otherN/AN/AN/A (Address out of range)
💡 Execution stops after outputting data for the given address; addresses outside 0-3 are invalid.
Variable Tracker
VariableStartAfter Step 1After Step 2After Step 3After Step 4Final
addressundefined"00""01""10""11"varies
address (int)undefined0123varies
dataundefined"0001""0010""0100""1000"varies
Key Moments - 3 Insights
Why do we convert the address from std_logic_vector to integer?
Because the constant array ROM_Array is indexed by integers (0 to 3), so we must convert the binary address to an integer to access the correct element, as shown in execution_table rows 1-4.
What happens if the input address is outside the defined range (0 to 3)?
The ROM_Array only has 4 elements indexed 0 to 3. An address outside this range is invalid and will cause an error or undefined behavior, as noted in execution_table row 5.
Why is the ROM_Array declared as a constant?
Declaring ROM_Array as a constant means its contents cannot change during simulation or synthesis, which models the read-only nature of ROM, ensuring data is fixed as shown in the concept_flow.
Visual Quiz - 3 Questions
Test your understanding
Look at the execution_table, what is the output data when the input address is "10"?
A"1000"
B"0010"
C"0100"
D"0001"
💡 Hint
Refer to execution_table row 3 where address "10" corresponds to output "0100".
At which step does the address convert from "01" to integer 1?
AStep 1
BStep 2
CStep 3
DStep 4
💡 Hint
Check execution_table row 2 for address "01" and its integer conversion.
If the ROM_Array size changed to 8 elements, how would the execution_table change?
AMore rows for addresses 0 to 7 would be added
BOutput data would remain the same for addresses 0 to 3 only
CAddress conversion would no longer be needed
DROM_Array would become variable instead of constant
💡 Hint
Consider how the ROM_Array size affects the number of valid addresses in execution_table rows.
Concept Snapshot
ROM using constant array in VHDL:
- Declare a constant array with fixed data.
- Use an input address (std_logic_vector).
- Convert address to integer to index array.
- Output data from array at that index.
- ROM data is read-only and fixed at compile time.
Full Transcript
This visual execution trace shows how to implement a ROM in VHDL using a constant array. First, a constant array named ROM_Array is defined with fixed 4-bit data values for addresses 0 to 3. The ROM entity has an input address and an output data port. When the address input changes, the process converts the std_logic_vector address to an integer index. This integer is used to access the corresponding element in ROM_Array. The data at that index is then assigned to the output port. The execution table traces each step with different addresses, showing the integer conversion and the output data. The variable tracker shows how the address and data variables change after each step. Key moments clarify why address conversion is needed, what happens with invalid addresses, and why the array is constant. The quiz tests understanding of address conversion, output data, and how changing ROM size affects the table. The concept snapshot summarizes the key points for quick reference.

Practice

(1/5)
1. What is the main purpose of using a constant array to implement ROM in VHDL?
easy
A. To generate random data values dynamically
B. To create a writable memory block for data storage
C. To perform arithmetic operations on data
D. To store fixed data that can be read by address during simulation or synthesis

Solution

  1. Step 1: Understand ROM functionality

    ROM (Read-Only Memory) stores fixed data that does not change during operation.
  2. Step 2: Role of constant array in VHDL

    A constant array holds fixed values accessible by address, perfect for ROM implementation.
  3. Final Answer:

    To store fixed data that can be read by address during simulation or synthesis -> Option D
  4. Quick Check:

    ROM = fixed data storage [OK]
Hint: ROM stores fixed data accessed by address only [OK]
Common Mistakes:
  • Confusing ROM with writable RAM
  • Thinking ROM can be changed during runtime
  • Using variable arrays instead of constant arrays
2. Which of the following is the correct way to declare a ROM using a constant array of 8-bit std_logic_vector in VHDL?
easy
A. constant ROM : array (0 to 3) of std_logic_vector(7 downto 0) := (x"01", x"02", x"04", x"08");
B. constant ROM : array (0 to 3) of std_logic_vector(7 downto 0) := ("0000001", "0000010", "0000100", "0001000");
C. constant ROM : array (0 to 3) of std_logic_vector(7 downto 0) := ("x01", "x02", "x04", "x08");
D. constant ROM : array (0 to 3) of std_logic_vector(7 downto 0) := (1, 2, 4, 8);

Solution

  1. Step 1: Check array declaration syntax

    In VHDL, constant arrays must be declared with proper type and range, here 0 to 3 for 4 elements.
  2. Step 2: Check value format for std_logic_vector

    Values must be std_logic_vector literals; hex notation x".." is correct for 8-bit vectors.
  3. Final Answer:

    constant ROM : array (0 to 3) of std_logic_vector(7 downto 0) := (x"01", x"02", x"04", x"08"); -> Option A
  4. Quick Check:

    Hex literals with x".." for std_logic_vector [OK]
Hint: Use x".." for hex std_logic_vector constants [OK]
Common Mistakes:
  • Using double quotes for hex values incorrectly
  • Assigning integers directly to std_logic_vector
  • Incorrect array type or syntax
3. Given the following VHDL ROM declaration and read process, what is the output on data_out when addr = "10" (binary 2)?
constant ROM : array (0 to 3) of std_logic_vector(7 downto 0) := (x"0A", x"1B", x"2C", x"3D");

process(addr) begin
  data_out <= ROM(to_integer(unsigned(addr)));
end process;
medium
A. x"2C"
B. x"1B"
C. x"0A"
D. x"3D"

Solution

  1. Step 1: Convert address to integer

    Address "10" in binary equals decimal 2.
  2. Step 2: Access ROM at index 2

    ROM(2) is x"2C" as per the constant array declaration.
  3. Final Answer:

    x"2C" -> Option A
  4. Quick Check:

    addr 2 accesses ROM(2) = x"2C" [OK]
Hint: Convert binary address to integer to index ROM [OK]
Common Mistakes:
  • Confusing binary "10" as decimal 10
  • Using unsigned conversion incorrectly
  • Accessing wrong ROM index
4. Identify the error in this VHDL ROM constant array declaration:
constant ROM : array (0 to 3) of std_logic_vector(7 downto 0) := (x"01", x"02", x"03");
medium
A. Hex values must be in single quotes, not double quotes
B. ROM array size does not match the number of elements assigned
C. std_logic_vector cannot be used in constant arrays
D. ROM must be declared as a variable, not constant

Solution

  1. Step 1: Check array range and element count

    Array declared from 0 to 3 means 4 elements expected.
  2. Step 2: Count assigned elements

    Only 3 elements are assigned, causing a size mismatch error.
  3. Final Answer:

    ROM array size does not match the number of elements assigned -> Option B
  4. Quick Check:

    Array size must equal element count [OK]
Hint: Match array range with number of elements exactly [OK]
Common Mistakes:
  • Assigning fewer elements than declared range
  • Misusing quotes for hex literals
  • Thinking constants can be variables
5. You want to create a 16-word ROM with 4-bit addresses and 8-bit data using a constant array in VHDL. Which of the following code snippets correctly implements this ROM and reads data based on the address input addr?
hard
A. constant ROM : array (0 to 15) of std_logic_vector(7 downto 0) := (others => (others => '0')); process(addr) begin data_out <= ROM(addr); end process;
B. constant ROM : array (0 to 15) of std_logic_vector(7 downto 0); process(addr) begin data_out <= ROM(addr); end process;
C. constant ROM : array (0 to 15) of std_logic_vector(7 downto 0) := (x"00", x"01", x"02", x"03", x"04", x"05", x"06", x"07", x"08", x"09", x"0A", x"0B", x"0C", x"0D", x"0E", x"0F"); process(addr) begin data_out <= ROM(to_integer(unsigned(addr))); end process;
D. constant ROM : array (0 to 15) of std_logic_vector(7 downto 0) := (x"00", x"01", x"02", x"03"); process(addr) begin data_out <= ROM(to_integer(unsigned(addr))); end process;

Solution

  1. Step 1: Check ROM declaration size and initialization

    ROM must have 16 elements (0 to 15) each 8-bit wide, fully initialized.
  2. Step 2: Verify address conversion and data read

    Address is 4-bit std_logic_vector, converted to integer with to_integer(unsigned(addr)) to index ROM correctly.
  3. Step 3: Validate code correctness

    constant ROM : array (0 to 15) of std_logic_vector(7 downto 0) := (x"00", x"01", x"02", x"03", x"04", x"05", x"06", x"07", x"08", x"09", x"0A", x"0B", x"0C", x"0D", x"0E", x"0F"); process(addr) begin data_out <= ROM(to_integer(unsigned(addr))); end process; correctly initializes all 16 elements and reads data using proper address conversion.
  4. Final Answer:

    constant ROM : array (0 to 15) of std_logic_vector(7 downto 0) := (x"00", x"01", x"02", x"03", x"04", x"05", x"06", x"07", x"08", x"09", x"0A", x"0B", x"0C", x"0D", x"0E", x"0F"); process(addr) begin data_out <= ROM(to_integer(unsigned(addr))); end process; -> Option C
  5. Quick Check:

    Full initialization + correct address indexing = constant ROM : array (0 to 15) of std_logic_vector(7 downto 0) := (x"00", x"01", x"02", x"03", x"04", x"05", x"06", x"07", x"08", x"09", x"0A", x"0B", x"0C", x"0D", x"0E", x"0F"); process(addr) begin data_out <= ROM(to_integer(unsigned(addr))); end process; [OK]
Hint: Initialize all ROM elements and convert address to integer [OK]
Common Mistakes:
  • Not initializing all ROM elements
  • Using addr directly without conversion
  • Declaring ROM without initialization
Recommended

Ready to prove it?

Pass the test and this pattern moves unknown strong while earning +1 Grip toward your certificate.

10 questions~5 mineasy hard