Search code examples
vhdlmodelsimquestasim

VHDL 2008 can't drive a signal with an alias of an external name


Please take a look at the following code, specifically the 3 commented lines at the end. I simulated this with Questasim 10.6c:

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

entity alias_extname_driving_signal is
port(
  clk : in std_logic
);
end alias_extname_driving_signal;

architecture primary of alias_extname_driving_signal is

  signal buried_control_vector16 : std_logic_vector(15 downto 0) := (others => '0');

begin

 buried_control_vector16 <= std_logic_vector(unsigned(buried_control_vector16) + 1) when rising_edge(clk);

end architecture primary;




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

entity alias_extname_driving_signal_tb is
end alias_extname_driving_signal_tb;

architecture primary of alias_extname_driving_signal_tb is

  signal clk : std_logic := '0';
  signal control_vector16 : std_logic_vector(15 downto 0) := (others => '0');
  alias control_vector16_alias is control_vector16;
  alias buried_control_vector16_alias is << signal .alias_extname_driving_signal_tb.uut.buried_control_vector16 : std_logic_vector(15 downto 0) >>;
  signal vector16 : std_logic_vector(15 downto 0);

begin

  clk <= not clk after 10 ns;

  control_vector16 <= std_logic_vector(unsigned(control_vector16) + 1) when rising_edge(clk);

  uut : entity work.alias_extname_driving_signal
  port map(
    clk => clk
  );

  -- vector16 <= << signal .alias_extname_driving_signal_tb.uut.buried_control_vector16 : std_logic_vector(15 downto 0) >>; -- this statement works
  -- vector16 <= control_vector16_alias; -- this statement works
  -- vector16 <= buried_control_vector16_alias; -- vector16 remains perpetually undefined with this statement

end architecture primary;

As you can see, I'm able to drive a signal with an external name, an alias of a local signal, but not an alias of an external name. Is there any way I can use an alias of an external name to drive a signal in vhdl-2008?

Thanks in advance for your help.


Solution

  • External names can only be declared AFTER the object being referenced is elaborated.

    VHDL starts elaborating from the testbench. First it elaborates the declaration region. Then it elaborates the code region in order. If it finds a component, it elaborates it and any subcomponents. When it finishes elaborating the component (and any subcomponents) it picks up elaborating int the testbench where it left off.

    Hence, you need to move your alias declaration to either a block statement or a process. The code for the block statement is as follows. Note the label with the block statement is required.

    architecture primary of alias_extname_driving_signal_tb is
    
      signal clk : std_logic := '0';
      signal control_vector16 : std_logic_vector(15 downto 0) := (others => '0');
      alias control_vector16_alias is control_vector16;
      signal vector16 : std_logic_vector(15 downto 0);
    
    begin
    
      clk <= not clk after 10 ns;
    
      control_vector16 <= std_logic_vector(unsigned(control_vector16) + 1) when rising_edge(clk);
    
      uut : entity work.alias_extname_driving_signal
      port map(
        clk => clk
      );
    
      myblock : block 
        alias buried_control_vector16_alias is << signal .alias_extname_driving_signal_tb.uut.buried_control_vector16 : std_logic_vector(15 downto 0) >>;
      begin
         vector16 <= << signal .alias_extname_driving_signal_tb.uut.buried_control_vector16 : std_logic_vector(15 downto 0) >>; -- this statement works
         vector16 <= control_vector16_alias; -- this statement works
         vector16 <= buried_control_vector16_alias; -- vector16 remains perpetually undefined with this statement
      end block myblock ; 
    
    end architecture primary;