如何重用实体来处理不同的组件



我对vhdl相当陌生,想知道管理以下情况/模式的最佳方法是什么:

假设我有一个实体 A,其体系结构实例化组件 B。然后我想重用 A,但这次实例化一个组件 C 代替 B.C 具有与 B 完全不同的功能.B 和 C 可能具有不同大小的端口,但是 A 的功能是它可以处理不同的端口大小,例如,使用泛型并生成语句。本质上,A就像组件B,C或D,E,F等的容器。它可能以所有这些组件通用的方式对 B、C 等的输入和输出执行一些逻辑/缓冲。

我已经阅读了有关配置的信息,我的理解是我可以实例化 A 中的组件(称为 Z(,然后使用配置将其实体链接到不同的体系结构。似乎没有多少人使用 vhdl 的这个功能。

在这种情况下,配置是正确的方法吗?

理想情况下,我希望设计中的所有参数最终都取决于为 Z 选择的架构,以便架构决定其链接到 (Z( 的实体的端口大小,反过来 Z 的端口大小决定 A 的参数,最后这些参数决定 A 的端口大小。这可能吗?

(我使用一般意义上的"参数化"来表示配置设计的一种方式。泛型、包、范围属性等都是参数化的例子(

下面是我的意思的伪代码示例。大写字母的值应取决于为 Z 选择的体系结构。

entity A is
port
(
clk             : in std_logic;
reset           : in std_logic;
inputs          : in std_logic_vector(SOME_WIDTH_A_IN - 1 downto 0);
outputs         : out std_logic_vector(SOME_WIDTH_A_OUT - 1 downto 0);
);
end A;
architecture A_arch of A is
component Z
port
(
clock       : in std_logic;
inputs      : std_logic_vector(SOME_WIDTH_Z_IN - 1 downto 0);
ouputs      : std_logic_vector(SOME_WIDTH_Z_OUT - 1 downto 0)
);
end component;
begin
for i in 1 to SOME_VALUE generate
-- whatever logic/buffering we want to perform on the inputs    
end generate;
for i in 1 to SOME_VALUE generate
-- whatever logic/buffering we want to perform on the outputs
end generate;
instance: Z   
port map(
clock => clk,
inputs => --output of logic/buffering above 
outputs => -- input of logic/buffering above
);
end A_arch;

我可能以错误的方式考虑了这一点 - 本质上,我想避免复制/粘贴"容器"实体 A 来处理不同的组件 B、C 等。最好的方法是什么?

似乎您希望您的组件 B、C、D 等执行完全相同的操作,除了不同的端口大小。最好的方法是使用通用。 假设您的另一个实体(我们称之为INNER_ENTITY(是可配置的 n 位宽双触发器(可用于解析亚稳态(。 以下是OUTER_ENTITY和INNER_ENTITY的示例代码:

library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
use IEEE.STD_LOGIC_UNSIGNED.ALL;
entity OUTER_ENTITY is
port (
CLK     : in    std_logic;
RST     : in    std_logic;
PORT_A  : in    std_logic_vector(6 downto 0);
PORT_B  : in    std_logic_vector(13 downto 0);
SUM_A_B : out   std_logic_vector(13 downto 0)
);
end entity;
architecture RTL_OUTER_ENTITY of OUTER_ENTITY is
signal PORT_A_INNER : std_logic_vector(6 downto 0);
signal PORT_B_INNER : std_logic_vector(13 downto 0);
component INNER_ENTITY
generic (PORT_SIZE : integer);
port (
CLK      : in   std_logic;
RST      : in   std_logic;
PORT_IN  : in   std_logic_vector(PORT_SIZE - 1 downto 0);
PORT_OUT : out  std_logic_vector(PORT_SIZE - 1 downto 0);
);
end component INNER_ENTITY;
begin
SUM_A_B <= PORT_A_INNER + PORT_B_INNER;
INNER_7_BIT : INNER_ENTITY
generic map (PORT_SIZE => 7)
port map (
CLK         => CLK,
RST         => RST,
PORT_IN     => PORT_A,
PORT_OUT    => PORT_A_INNER
);
INNER_14_BIT : INNER_ENTITY
generic map (PORT_SIZE => 14)
port map (
CLK         => CLK,
RST         => RST,
PORT_IN     => PORT_B,
PORT_OUT    => PORT_B_INNER
);
end RTL_OUTER_ENTITY;   
entity INNER_ENTITY
generic (PORT_SIZE : integer);
port (
CLK      : in   std_logic;
RST      : in   std_logic;
PORT_IN  : in   std_logic_vector(PORT_SIZE - 1 downto 0);
PORT_OUT : out  std_logic_vector(PORT_SIZE - 1 downto 0);
);
end entity;
architecture RTL_INNER_ENTITY of INNER_ENTITY is
signal  PORT_X :  std_logic_vector(PORT_SIZE - 1 downto 0);
begin
process(CLK, RST)
begin
if RST = '1' then
PORT_OUT <= (OTHERS => '0');
PORT_X   <= (OTHERS => '0');
elsif rising_edge(CLK) then
PORT_OUT <= PORT_X;
PORT_X <= PORT_IN;
end if;
end process;
end RTL_INNER_ENTITY;

请注意,我没有编译此代码,因此它可能有一些小的语法错误,但它应该为您提供如何使用 GENERICS 来执行您想要的操作的概述。

最新更新