是否有一种简单的方法来实现以下行:
DataTX(255-index*8 downto 248-index*8) <= encoded;
index是一个整数,可以在0到31之间。
DataTx是STD_LOCIC_VECTOR(263 downto 0)。
现在它发出一个错误,说DataTx(263)和DataTx(260)有多个驱动程序,但实际上并没有在这一行中发生。
有没有办法编写这一行或实现它,而无需执行大量的if语句或case语句。
先谢谢你。
编辑: 上面的行放在一个过程中。 同时,DataTx的其他部分在该过程之外设置如下
DataTX(263 downto 261) <= "000" when spi_mode=reading else "001" when spi_mode=writing
else "011" when spi_mode=rxMode else "101" when spi_mode=txMode;
DataTX(260 downto 256) <= SPI_register;
EDIT2:
DataTX(263 downto 261) <= "000" when spi_mode=reading else "001" when spi_mode=writing
else "011" when spi_mode=rxMode else "101" when spi_mode=txMode;
DataTX(260 downto 256) <= SPI_register;
-- Set the RF Chan based on input
rf_chan <= RfChans(0) when base_selection="00" else RfChans(1) when base_selection="01" else
RfChans(2) when base_selection="10" else RfChans(3) when base_selection="11";
-- Set the Base Address based on input
base_addr <= Bases(0) when base_selection="00" else Bases(1) when base_selection="01" else
Bases(2) when base_selection="10" else Bases(3) when base_selection="11";
process(clk)
variable s_index : integer range 0 to 31 := 0;
variable e_index : integer range 0 to 31 := 0;
variable r_index : integer range 0 to 31 := 0;
variable counter : integer range 0 to 7 := 0;
begin
if (rst = '1') then
...
elsif (clk'event and clk='1') then
case state is
when setup =>
case setup_state is
-- Some code like this is set here
spi_mode <= writing;
spi_register <= "10000";
DataTX(255 downto 224) <= base_addr;
DataTX(223 downto 0) <= (others => '1'); -- Fill with FF
when idle =>
... -- nothing here of relevance
-- Moves to E_setup
when E_setup =>
-- DataTx set here
spi_mode <= writing;
spi_register <= "00000";
SPI_trigger <= '1';
state <= E_setupd;
when E_setupd => -- one cycle delay
SPI_Trigger <= '0';
if ((counter = 7) and SS='1') then
-- Signals that SPI module has finished
state <= E_encode;
counter := 0;
elsif (counter < 7) then -- Give it some time to start
counter := counter +1;
end if;
when E_encode =>
encode_input <= SEQUENCE(e_index);
e_index := e_index +1;
state <= E_done;
when E_done =>
spi_register <= "00000";
-- Error here
DataTX(255-index*8 downto 248-index*8) <= encoded;
if (e_index = 31) then
e_index := 0;
state <= E_send;
else
e_index := e_index +1;
state <= E_encode;
end if;
end case;
end if;
end process;
答案 0 :(得分:1)
更新的问题提供了足够的信息来尝试答案。 它归结为什么是&#34;本地静态&#34;即可在不实际执行过程的情况下进行计算,以便可以合成硬件以满足规范。
现在你可能很明显
DataTX(<arbitrary range expression>) <= encoded;
仅驱动DataTX
的选定部分,而不评估<arbitrary range expression>
,但合成工具并不那么聪明。因此语言对过程施加了限制,即本地静态&#34;表达式是DataTX
的全部,因此该过程驱动所有DataTX
。
(注意:范围表达式纯粹是根据常量或数字文字,这个限制不适用)
外部作业然后形成您的额外司机,从而产生多个司机&#34;错误。
两个修正:
1)在整个过程中驱动整个DataTX
,即在过程中移动其他切片分配......这对我来说看起来像是不洁净的设计
2)分配新信号,例如进程中EncodedTX
,并从外部将其分配给正确的DataTX片段
DataTX(255 downto 0) <= EncodedTX;
或更好(更清晰的设计意图)
DataTX <= SPI_Mode_Bits & SPI_Register & Encoded_TX;
为SPI_Mode_Bits
信号提供合适的声明和分配。
可能还有其他修复,但其中第二个可能是我的第一选择......
鉴于Edit2,我现在相信选项(1)更清晰:例如分配主状态机进程中的额外位,无论如何都是设置SPI_Mode和SPI_Register的位置。您甚至可以为相关的Data_TX片段创建SPI_Register别名。然后,您不需要在SM和支持它之间的外部残差之间进行交叉引用。
例如,请考虑以下声明:
alias SPI_Register : std_logic_vector(4 downto 0) is DataTX(260 downto 256);
subtype SPI_Mode_Type is std_logic_vector(2 downto 0);
alias SPI_Mode : SPI_Mode_Type is DataTX(263 downto 261);
constant writing : SPI_Mode_Type := "001"; -- and a few more of these
状态机无需更改,现在将执行Datatx的所有分配,并且可以简单地删除外部分配。