-- $Id: bitcount.vhd,v 1.2 2002/02/06 22:29:12 lemieux Exp lemieux $ LIBRARY ieee; USE ieee.std_logic_1164.all; LIBRARY work; USE work.components.shiftrne; ENTITIY bitcount IS PORT( clock, resetn : IN STD_LOGIC; s : IN STD_LOGIC; data : IN STD_LOGIC_VECTOR(7 DOWNTO 0); B : BUFFER INTEGER RANGE 0 TO 8; done : OUT ); END bitcount; ARCHITECTURE Behavior OF bitcount IS TYPE StateType IS (S1, S2, S3); SIGNAL y : StateType; SIGNAL A : STD_LOGIC_VECTOR(7 DOWNTO 0); SIGNAL z,EA,LA,EB,LB,shiftin : STD_LOGIC; BEGIN -- ********************************************************************** -- datapath A=0 condition (combinational logic) z <= '1' WHEN A="00000000" ELSE '0'; -- NOR gate -- ********************************************************************** -- datapath shiftreg (sequential logic) -- the VHDL code for this is in Figure 8.48 (p.469) of DL text. shiftin <= '0'; ShiftA: shiftrne GENERIC MAP (N=>8) PORT MAP ( data, LA, EA, shiftin, clock, A ); -- ********************************************************************** -- datapath counter (sequential logic) upcount: PROCESS( resetn, clock ) -- note: this process is made ACTIVE any time resetn or clock change. -- it will be evaluated sequentially, from BEGIN to END, -- to create a change in the system. the process will then -- go dormant until the next change of resetn or clock. BEGIN IF resetn = '0' THEN B <= 0; ELSIF( clock'EVENT AND clock='1' ) THEN IF EB='1' THEN IF LB='1' THEN B <= 0; ELSE B <= B + 1; END IF; END IF; END IF; END PROCESS; -- ********************************************************************** -- control FSM (sequential logic) FSMcontrol: PROCESS( resetn, clock ) BEGIN IF resetn = '0' THEN y <= S1; ELSIF( clock'EVENT AND clock='1' ) THEN CASE y IS WHEN S1 => if s='0' THEN y<=S1; ELSE y<=S2; END IF; WHEN S2 => if z='0' THEN y<=S2; ELSE y<=S3; END IF; WHEN S3 => if s='0' THEN y<=S1; ELSE y<=S3; END IF; END CASE; END IF; END PROCESS; -- ********************************************************************** -- FSM Mealy outputs (combinational logic) FSMoutputs: PROCESS( y, s, A(0), z ) -- note: no clock, resetn in sensitivity list. this process -- becomes ACTIVE and outputs change ANYTIME one of -- y, s, A(0), z change. BEGIN -- default values EA <= '0'; LA <= '0'; EB <= '0'; LB <= '0'; done <= '0'; -- since we are in a process, we can assign new values to EA, etc -- without getting a "multiply assigned" error. only the LAST -- assignment will take effect. CASE y IS WHEN S1 => LB <= '1'; EB <= '1'; IF s='0' THEN LA <='1'; EA <='1'; END IF; WHEN S2 => EA <= '1'; -- note: we're not testing z here -- as shown in the ASM chart -- because A(0)='0' implies z='0' IF A(0)='1' THEN EB <='1'; END IF; WHEN S3 => done <= '1'; IF s='0' THEN -- optional LA <='1'; EA <='1'; END IF; END CASE END PROCESS; END Behavior;