pp.303-305
00秒から59秒までカウントするタイマーを作る。
バイナリーカウンターでカウントしてからBCDに変換するのではなく、10進1桁ごとに4ビットBCDカウンターを設けて出力する。ここではアノードコモン1桁を2個使った。ダイナミック点灯はせずに個別にドライブした。
library ieee; use ieee.std_logic_1164.all; entity timer is generic( F_CLK: integer := 1000 ); port( clk, ena : in std_logic; digit1, digit2: out std_logic_vector(6 downto 0) ); end entity; architecture rtl of timer is constant MODULO_0: natural := F_CLK; constant MODULO_1: natural := 10; constant MODULO_2: natural := 6; function int_to_ssd (input: integer) return std_logic_vector is begin case input is -- gfedabc, anode common. when 0 => return "1000000"; when 1 => return "1111100"; when 2 => return "0100001"; when 3 => return "0110000"; when 4 => return "0011100"; when 5 => return "0010010"; when 6 => return "0000010"; when 7 => return "1111000"; when 8 => return "0000000"; when 9 => return "0010000"; when 10 => return "0001000"; when 11 => return "0000110"; when 12 => return "1000011"; when 13 => return "0100100"; when 14 => return "0000011"; when 15 => return "0001011"; when others => return "0111111"; end case; end function; begin process(clk) variable count0: natural range 0 to MODULO_0; variable count1: natural range 0 to MODULO_1; variable count2: natural range 0 to MODULO_2; begin if rising_edge(clk) and (ena='1')then count0 := count0 + 1; -- クロックカウンターをインクリメントして、 if count0 = MODULO_0 then -- クロックカウンターがモジュロに達したら、 count0 := 0; -- クロックカウンターをリセットすると同時に、 count1 := count1 + 1; -- 1桁目カウンターをインクリメントして、 if count1 = MODULO_1 then -- 1桁目カウンターがモジュロに達したら、 count1 := 0; -- 1桁目カウンターをリセットすると同時に、 count2 := count2 + 1; -- 2桁目タウンターをインクリメントして、 if count2 = MODULO_2 then -- 2桁目カウンターがモジュロに達したら、 count2 := 0; -- 2桁目カウンターをリセットする。 end if; end if; end if; end if; digit1 <= int_to_ssd(count1); digit2 <= int_to_ssd(count2); end process; end architecture;