timeout counter implemented, starting FSM that controls UART <=> Wishbone transfers

This commit is contained in:
Mario Hüttel 2017-11-23 00:25:09 +01:00
parent ff25a4dabf
commit 7dec75c52e
1 changed files with 84 additions and 27 deletions

111
top.vhd
View File

@ -3,10 +3,10 @@
-- Project : tiny-xo2
-------------------------------------------------------------------------------
-- File : top.vhd
-- Author : マリオ <mario.huettel@gmx.net>
-- Author : Mario Hüttel <mario.huettel@gmx.net>
-- Company :
-- Created : 2017-11-21
-- Last update: 2017-11-22
-- Last update: 2017-11-23
-- Platform :
-- Standard : VHDL'93/02
-------------------------------------------------------------------------------
@ -36,30 +36,37 @@ end entity config_top;
architecture RTL of config_top is
type fsm_state_t is (IDLE, CMD, REPLY, HANG);
----------------- RESET LOGIC ------------------------------
signal dts_sync : std_logic_vector(2 downto 0) := (others => '0');
signal rst : std_logic; -- reset (high active)
signal dts_sync : std_logic_vector(2 downto 0) := (others => '0');
signal rst : std_logic; -- reset (high active)
----------------- UART RX ----------------------------------
signal data_rx : std_logic_vector(7 downto 0);
signal byte_ready_rx : std_logic;
signal error_rx : std_logic;
signal data_rx : std_logic_vector(7 downto 0);
signal byte_ready_rx : std_logic;
signal error_rx : std_logic;
----------------- UART TX ----------------------------------
signal data_tx : std_logic_vector(7 downto 0);
signal byte_ready_tx : std_logic;
signal busy_tx : std_logic;
signal config_busy : std_logic := '1'; -- indicates that the core is in configuration/waiting mode
-- and the user logic has to stay in reset
signal data_tx : std_logic_vector(7 downto 0);
signal byte_ready_tx : std_logic;
signal busy_tx : std_logic;
signal config_busy : std_logic := '1'; -- indicates that the core is in configuration/waiting mode
-- and the user logic has to stay in reset
signal config_active : std_logic := '1'; -- configuration FSM active
---------------------------- Wishbone Bus -------------------------------------
signal wb_cyc : std_logic;
signal wb_stb : std_logic;
signal wb_we : std_logic;
signal wb_adr : std_logic_vector(7 downto 0);
signal wb_dat_in : std_logic_vector(7 downto 0);
signal wb_dat_out : std_logic_vector(7 downto 0);
signal wb_ack : std_logic;
signal wb_cyc : std_logic;
signal wb_stb : std_logic;
signal wb_we : std_logic;
signal wb_adr : std_logic_vector(7 downto 0);
signal wb_dat_in : std_logic_vector(7 downto 0);
signal wb_dat_out : std_logic_vector(7 downto 0);
signal wb_ack : std_logic;
-------------------------------- State machine -----------------------------------
signal state : fsm_state_t;
signal reply_is_error : std_logic;
signal bytecounter : integer range 0 to 3 := 0;
begin -- architecture RTL
@ -80,7 +87,6 @@ begin -- architecture RTL
wb_ack_o => wb_ack,
wbc_ufm_irq => open);
uart_rx_1 : entity work.uart_rx
port map (
clk => clk,
@ -108,11 +114,25 @@ begin -- architecture RTL
tx => uart_tx);
timeout_counter_gen : process(clk) is
variable cnt : integer range 0 to 40000;
-- set config_busy on reset and wait 0.25s. If FSM is not active
-- deassert config_busy
timeout_counter_busy_gen : process(clk, rst) is
variable cnt : integer range 0 to 3000000 := 3000000; -- 0.25 sec counter
begin
-- TODO: implement timeout counter
end process timeout_counter_gen;
if rst = '1' then
cnt := 3000000;
config_busy <= '1';
elsif rising_edge(clk) then
config_busy <= '1';
if cnt /= 0 then
cnt := cnt - 1
else
if config_active = '0' then
config_busy <= '0';
end if;
end if;
end if;
end process timeout_counter_busy_gen;
-- Generate reset pulse on rising edge of dts input
@ -141,6 +161,43 @@ begin -- architecture RTL
end process user_logic_reset_gen;
controlFSM : process (clk, rst) is
begin -- process controlFSM
if rst = '1' then
state <= IDLE;
config_active <= '0';
bytecounter <= 0;
reply_is_error <= '0';
-- Wishbone
wb_cyc <= '0';
wb_stb <= '0';
wb_adr <= (others => '0');
wb_dat_in <= (others => '0');
-- UART TX
data_tx <= (others => '0');
byte_ready_tx <= '0';
elsif rising_edge(clk) then
case state is
when IDLE =>
if byte_ready_rx = '1' and data_rx = x"D5" then -- Serial byte received. Is it the preambel?
state <= CMD;
bytecounter <= 0;
end if;
when CMD =>
if byte_ready_rx = '1' then
-- TODO: Byte received. Do something
end if;
when REPLY =>
-- TODO: if reply_is_error = '1' then: wait for response that
-- indicates that the error is handled. Then switch back to command
-- mode. Else; Just wait for response to be sent.
null;
when HANG =>
state <= HANG; -- End of FSM. Only way out is a reset
end case;
end if;
end process controlFSM;
------ Asynchronous output assignments ---------------