library IEEE; use IEEE.STD_LOGIC_1164.ALL; use IEEE.STD_LOGIC_ARITH.ALL; use IEEE.STD_LOGIC_UNSIGNED.ALL; library work; use work.usefuls.ALL; entity DividerN is generic ( divide_value : positive := 8 ); port ( clk : in std_logic; reset : in std_logic; clk_out : out std_logic; tc : out std_logic ); end DividerN; architecture RTL of DividerN is constant required_bits : integer := min_bits(mod_even(divide_value) - 1); signal timer : std_logic_vector(required_bits - 1 downto 0); -- := (others => '0'); signal clk_out_pos : std_logic; signal clk_out_neg : std_logic; begin gen_even: if (divide_value mod 2 = 0) generate u0: process (clk, reset) begin if (reset = '1') then timer <= (others => '0'); clk_out <= '1'; -- registered output tc <= '0'; -- registered output elsif (clk'event and clk = '1') then if (timer = 0) then timer <= timer + 1; clk_out <= '1'; tc <= '1'; elsif (timer >= conv_std_logic_vector(divide_value - 1, required_bits)) then timer <= (others => '0'); clk_out <= '0'; tc <= '0'; elsif (timer >= conv_std_logic_vector(divide_value / 2, required_bits)) then timer <= timer + 1; clk_out <= '0'; tc <= '0'; else timer <= timer + 1; clk_out <= '1'; tc <= '0'; end if; end if; end process; end generate; gen_odd: if (divide_value >= 3) and (divide_value mod 2 = 1) generate u0: process (clk, reset) begin if (reset = '1') then timer <= (others => '0'); clk_out_pos <= '1'; -- registered output tc <= '0'; -- registered output elsif (clk'event and clk = '1') then if (timer = 0) then timer <= timer + 1; clk_out_pos <= '1'; tc <= '1'; elsif (timer >= conv_std_logic_vector(divide_value - 1, required_bits)) then timer <= (others => '0'); clk_out_pos <= '0'; tc <= '0'; elsif (timer >= conv_std_logic_vector(divide_value / 2, required_bits)) then timer <= timer + 1; clk_out_pos <= '0'; tc <= '0'; else timer <= timer + 1; clk_out_pos <= '1'; tc <= '0'; end if; end if; end process; u1: process (clk, reset) begin if (reset = '1') then clk_out_neg <= '1'; -- registered output elsif (clk'event and clk = '0') then -- NEG EDGE clk_out_neg <= clk_out_pos; end if; end process; clk_out <= clk_out_pos or clk_out_neg; -- NO HAZARD end generate; gen_unity: if (divide_value = 1) generate tc <= '0' when reset = '1' else clk; clk_out <= clk; end generate; end RTL;