Good time to everyone.
Resently I try to improve code in new project and found some interesting decoder. It has 2 processes: in first all data formed and in second all bus triggered in out registers by control signal. But some wires need to be reset in some period of time (in second process).
So I deside to write this code for correct resettind some signals ([cm_regA/cm_regB] are records with different types of data):
----------------------------------------
LOAD_DATA_PROCESS: process(clk_i)
begin
if rising_edge(clk_i) then
if (reset_reg) then
cm_regB.reg_1 <= '0';
cm_regB.reg_2 <= '0';
cm_regB.reg_3 <= '0';
cm_regB.reg_4 <= '0';
else
if (load_reg) then
cm_regB <= cm_regA;
else null;
end if;
end if;
end if;
end process;
----------------------------------------
But this construction Synthesized with lot of multiplexers betwen reg_5...reg_10, so next code give me good synthesized construction and great speed:
----------------------------------------
LOAD_DATA_PROCESS: process(clk_i)
begin
if rising_edge(clk_i) then
if (reset_reg) then
cm_regB.reg_1 <= '0';
cm_regB.reg_2 <= '0';
cm_regB.reg_3 <= '0';
cm_regB.reg_4 <= '0';
else
if (load_reg) then
cm_regB.reg_1 <= cm_regA.reg_1;
cm_regB.reg_2 <= cm_regA.reg_2;
cm_regB.reg_3 <= cm_regA.reg_3;
cm_regB.reg_4 <= cm_regA.reg_4;
else null;
end if;
end if;
if (load_reg) then
cm_regB.reg_5 <= cm_regA.reg_5;
cm_regB.reg_6 <= cm_regA.reg_6;
cm_regB.reg_7 <= cm_regA.reg_7;
cm_regB.reg_8 <= cm_regA.reg_8;
cm_regB.reg_9 <= cm_regA.reg_9;
cm_regB.reg_10 <= cm_regA.reg_10;
else null;
end if;
end if;
end process;
----------------------------------------
So the questions next:
P.S. Type of cm_regA and cm_regB are declarated in package. Here it is:
----------------------------------------
type cm_t is record
reg_1 : STD_LOGIC;
reg_2 : STD_LOGIC;
reg_3 : STD_LOGIC;
reg_4 : STD_LOGIC;
reg_5 : STD_LOGIC;
reg_6 : BOOLEAN;
reg_7 : STD_LOGIC;
reg_8 : STD_LOGIC;
reg_9 : STD_LOGIC_VECTOR(CONST_1-1 downto 0);
reg_10 : STD_LOGIC_VECTOR(CONST_2-1 downto 0);
end record cm_t;
----------------------------------------
In the case of your first code, you are indeed adding a dependency to reset
for reg_5
to reg_10
. This is because of the if-else statement. This is the effective code you write for these registers.
if not(reset_reg) and load_reg then
cm_regB.reg_5 <= cm_regA.reg_5;
[...]
cm_regB.reg_10 <= cm_regA.reg_10;
end if;
So, you should separate the reset block from the other assignment. You can achieve that by using the fact that for signals only the last assignment in a process will be applied the next delta cycle. So something like this:
LOAD_DATA_PROCESS: process(clk_i)
begin
if rising_edge(clk_i) then
if load_reg then
cm_regB <= cm_regA;
end if;
if reset_reg then
cm_regB.reg_1 <= '0';
cm_regB.reg_2 <= '0';
cm_regB.reg_3 <= '0';
cm_regB.reg_4 <= '0';
end if;
end if;
end process;