Search code examples
vhdlmodelsim

No Output From Entity in ModelSim Simulator - VHDL


I have written a simple entity in VHDL to blink an LED and am trying to simulate it in ModelSim but am getting no transitions on the output.

Here is my HDL file for the LED_Blink entity:

Library IEEE;
use IEEE.Std_logic_1164.all;

entity LED_Blink is

generic (
    g_SYSTEM_CLOCK_PERIOD   : in time := 10 ns; -- 100 MHz clock period
    g_LED_ON_TIME           : in time := 1 sec
);

port(
    system_clock    : in Std_logic; 
    reset_fpga_L    : in Std_logic;

    led_out         : out Std_logic
);
end entity LED_Blink;

architecture RTL of LED_Blink is
    signal led_state : Std_logic;
    constant COUNTER_RELOAD_VAL : natural := g_LED_ON_TIME/g_SYSTEM_CLOCK_PERIOD;
begin
    process(reset_fpga_L, system_clock)
        variable counter : natural range 0 to COUNTER_RELOAD_VAL := COUNTER_RELOAD_VAL;
    begin
        if reset_fpga_L = '0' then
            counter := COUNTER_RELOAD_VAL;
            led_state <= '0';
        elsif rising_edge(system_clock) then
            if counter = 0 then
                led_state <= not led_state;
                counter := COUNTER_RELOAD_VAL;
            else
                counter := counter - 1;
            end if;            
        end if;

        led_out <= led_state;
    end process;
end architecture RTL;

And here is my test-bench:

Library IEEE;
use IEEE.Std_logic_1164.all;

entity LED_Blink_TB is
end entity LED_Blink_TB;

architecture RTL of LED_Blink_TB is

    signal reset_fpga_L : Std_logic := '0';
    signal system_clock : Std_logic := '0';

    signal led_out      : Std_logic := '0';

begin

    G1: entity work.LED_Blink(RTL) port map(reset_fpga_L, system_clock, led_out);

    CLK: process
    begin
        while now <= 5 sec loop
            system_clock <= not system_clock;
            wait for 5 ns;
        end loop;
        wait;
    end process CLK;

    STIM: process
    begin
        reset_fpga_L <= '0';
        wait for 100 ns;
        reset_fpga_L <= '1';
        wait for 4 sec;
        reset_fpga_L <= '0';
        wait for 50 ns;
        reset_fpga_L <= '1';
        wait;
    end process STIM;

end architecture RTL;

I can't figure out why I'm not seeing any transitions on led_out when I run my test-bench in the simulator. I've taken care to add the waves for system_clock, reset_fpga_L, and led_out to the trace view. Do you see anything in my code that might be an issue? Thanks for your help.


Solution

  • A second form of the testbench can be used make generation of inputs to LED_Blink depend on the values supplied as generics:

    library ieee;
    use ieee.std_logic_1164.all;
    
    entity led_blink_tb is
    end entity;
    
    architecture foo of led_blink_tb is
        constant CLK_PERIOD:    time := 100 ms;
        constant LED_ON:        time := 500 ms;
        signal clk:             std_logic := '0';
        signal reset_n:         std_logic;
        signal led:             std_logic;
    begin
    DUT:
        entity work.led_blink
            generic map ( CLK_PERIOD, LED_ON)
            port map (
                system_clock => clk,
                reset_fpga_l => reset_n,
                led_out => led
            );
    CLOCK:
        process
        begin
            wait for CLK_PERIOD/2;
            clk <= not clk;
            if now > 2.5 sec then
                wait;
            end if;
        end process;
    STIMULI:
        process
        begin
            reset_n <= '0';
            wait for CLK_PERIOD * 2;
            reset_n <= '1';
            wait;
        end process;
    end architecture;
    

    The idea, both the testbench and the model depend on constants supplied as generics making changing the parameters require less work.

    Also note the association list in the port map uses named association.

    If we take a look at the original testbench port map:

    G1: entity work.LED_Blink(RTL) port map(reset_fpga_L, system_clock, led_out);
    

    We see that the first positional association to the formal system_clock is associated with the actual reset_fpga_L while the second positional association representing formal reset_fpga_L is associated with the actual system_clock.

    The two actual associations are in reversed order.