Один хороший способ сделать процессы с конечными автоматами более читабельными - это объединить общий код с процедурами, определенными в процессе. Например:
process (empty) is
procedure assign_something (
index : natural;
something : std_logic_vector(7 downto 0)
next_state : state_type
) is
begin
bus(index*8+7 downto index*8) <= something;
state <= next_state;
end procedure;
begin
wait until rising_edge(clk);
case state is
when st0_idle => ...
when st1_work0 => assign_something(0, something, st0_idle);
when st1_work1 => assign_something(1, something_else, st0_idle);
-- ... etc ...
end case;
if reset = '1' then
state <= st0_idle;
end if;
end procedure;
Надеюсь, вы поняли идею. В зависимости от того, насколько регулярна структура конечного автомата, вы также можете заменить перечисленные переменные состояния, которые соответствуют каждому индексу, на простой счетчик или переменную индекса, которую вы отслеживаете вместе с именованным состоянием.
Это все на ваше усмотрение, но, как бы вы это ни делали, использование процедур для выделения общего кода, когда это возможно, вероятно, значительно упростит работу с вашим VHDL.
Применение этого изменения приведет к тому, что код будет выглядеть примерно так:
architecture ...
type state_type is (st_idle, st_work);
signal state : state_type;
signal index : integer range 0 to NUM-1;
...
begin
...
process (empty) is
procedure assign_something (
index : natural;
something : std_logic_vector(7 downto 0)
next_state : state_type
) is
begin
bus(index*8+7 downto index*8) <= something;
state <= next_state;
end procedure;
begin
wait until rising_edge(clk);
case state is
when st_idle =>
for i in 0 to NUM-1 loop
if empty(i) = '1' then
index := i;
exit;
end if;
end loop;
when st_work => assign_something(index, something, st_idle);
end case;
if reset = '1' then
state <= st_idle;
end if;
end procedure;
Очевидно, что это должно быть изменено, чтобы точно соответствовать тому, что вы хотите сделать ... =)