library IEEE; use IEEE.STD_LOGIC_1164.ALL; use IEEE.STD_LOGIC_ARITH.ALL; use IEEE.STD_LOGIC_UNSIGNED.ALL; -- Uncomment the following lines to use the declarations that are -- provided for instantiating Xilinx primitive components. --library UNISIM; --use UNISIM.VComponents.all; entity vconfig is Port ( RES : in std_logic; nINIT_B : in std_logic; CLK : in std_logic; DONE : in std_logic; CCLK : out std_logic; CCLK_PRESCALER : in std_logic_vector(5 downto 0); LOAD_PRESCALER : in std_logic; DIN : in std_logic_vector(31 downto 0); DOUT : out std_logic; LOAD_SREG : in std_logic; BUF_IS_EMPTY : inout std_logic); end vconfig; architecture Behavioral of vconfig is constant nbits : integer := 32; constant nBufs : integer := 2; type t_config_state is (CFG_STOP, CFG_INIT, CFG_RUN); type t_buf is array (0 to nBufs-1) of std_logic_vector (nBits-1 downto 0); signal REG: t_buf; signal count, CLK_SCALE: integer range 0 to 63; signal SHIFT_CNT: integer range 0 to nbits-1; signal state, next_state : t_config_state; signal SCLK, SHIFT_EN : STD_LOGIC; signal buf_depth: integer range 0 to 2; signal tempID, readBufId, writeBufId : integer range 0 to nBufs-1; begin -- 4-bit loadable serial-in and serial-out shift register -- CLK: in STD_LOGIC; -- DIN: in STD_LOGIC; -- LOAD: in STD_LOGIC; -- LOAD_DATA: in STD_LOGIC_VECTOR(3 downto 0); -- DOUT: out STD_LOGIC; process (RES, SCLK, state, nINIT_B, DONE, REG, BUF_IS_EMPTY) begin if (RES = '1') then CCLK <= '1'; SHIFT_EN <= '0'; DOUT <= 'Z'; else case state is when CFG_STOP => SHIFT_EN <= '0'; CCLK <= '1'; if (DONE = '0' and BUF_IS_EMPTY = '0') then next_state <= CFG_INIT; else next_state <= CFG_STOP; end if; when CFG_INIT => CCLK <= SCLK; next_state <= CFG_RUN; when CFG_RUN => SHIFT_EN <= '1'; CCLK <= SCLK; if (DONE = '1' or nINIT_B = '0' or BUF_IS_EMPTY = '1') then next_state <= CFG_STOP; else next_state <= CFG_RUN; end if; end case; if (nINIT_B = '1') then DOUT <= STD_LOGIC(REG(readBufId)(nbits-1)); else DOUT <= 'Z'; end if; end if; end process; sreg: process(RES, SCLK, REG, DIN, LOAD_SREG, SHIFT_EN, SHIFT_CNT) begin if (RES = '1') then BUF_IS_EMPTY <= '1'; SHIFT_CNT <= 0; writeBufId <= 0; readBufId <= 0; buf_depth <= 0; elsif (LOAD_SREG = '1') then REG(writeBufId) <= DIN; if (SHIFT_EN = '0') then SHIFT_CNT <= nbits-1; end if; if (buf_depth = nbufs) then buf_depth <= buf_depth ; else buf_depth <= buf_depth + 1; end if; else if SCLK='0' and SCLK'event then if SHIFT_EN = '1' then REG(readBufId)(nbits-1 downto 0) <= REG(readBufId)(nbits-2 downto 0) & '0'; if (SHIFT_CNT = 0) then if (buf_depth = 0) then writeBufId <= 0; readBufId <= 0; else SHIFT_CNT <= nbits-1; tempID <= readBufID; readBufID <= writeBufId; writeBufId <= tempID; buf_depth <= buf_depth - 1; end if; else SHIFT_CNT <= SHIFT_CNT - 1; end if; end if; end if; end if; if (SHIFT_CNT = 0 and buf_depth = 1) then BUF_IS_EMPTY <= '1'; else BUF_IS_EMPTY <= '0'; end if; end process; -- 4-bit synchronous counter with count enable, -- asynchronous reset -- CLK: in STD_LOGIC; -- RESET: in STD_LOGIC; -- CE, LOAD, DIR: in STD_LOGIC; -- DIN: in STD_LOGIC_VECTOR(3 downto 0); -- COUNT: inout STD_LOGIC_VECTOR(3 downto 0); cfg_state_gen: process(RES, SCLK, next_state) begin if (RES = '1') then state <= CFG_STOP; elsif SCLK='1' and SCLK'event then state <= next_state; end if; end process; clk_prescaler: process (RES, CLK, CCLK_PRESCALER, LOAD_PRESCALER) begin if (RES = '1') then SCLK <= '1'; CLK_SCALE <= 1; COUNT <= CLK_SCALE; elsif (LOAD_PRESCALER = '1') then CLK_SCALE <= CONV_INTEGER(CCLK_PRESCALER); elsif CLK='1' and CLK'event then if (COUNT = 1) then SCLK <= not SCLK; COUNT <= CLK_SCALE; else COUNT <= COUNT - 1; end if; end if; end process; end Behavioral;