I am attempting to implement a tachometer interface that will accept digital pulses as an input. I simply count clk rising edges (50Mhz) between each rising edge of the tacho pulses (1Mhz). I have found examples on the web that achieve what I need to do, but in an attempt to not make the same mistakes in the future I would like to understand why this solution doesn't work.
When I say doesn't work I mean post-synthesis functional simulation doesn't produce the results I would expect. The behavioral simulation does output the values I was expecting.
In summary, synthesis appears to be ignoring my attempt to reset a variable to 0 (see comment 'this does not appear to execute' below). The tacho_count output increments without resetting. See simulation plots below.
entity tacho_interface is Generic ( FREQ_DIVISOR : integer := 6; MIN_RPM : integer := 200 ); Port ( enable : in STD_LOGIC; clk : in STD_LOGIC; pump_tacho : in STD_LOGIC; tacho_count : out STD_LOGIC_VECTOR(31 downto 0); error: out STD_LOGIC := '0' ); end tacho_interface; architecture Behavioral of tacho_interface is begin process variable last_tacho : std_logic := '1'; variable tracking_cntr : integer := 0; begin if (clk'event and clk = '1') then if (pump_tacho = '1' and pump_tacho /= last_tacho) then tacho_count <= std_logic_vector(to_unsigned(tracking_cntr * FREQ_DIVISOR, tacho_count'length)); wait for 0ns; tracking_cntr := 0; --this does not execute end if; last_tacho := pump_tacho; tracking_cntr := tracking_cntr + 1; end if; wait on clk; end process; end Behavioral;
Post-Synthesis Simulation illustrating problem (accumulation without reset to 0)
Behavioral Simulation illustrating what I expected