From 901cccd7da4af43bc0d88f7b6d14a8e473bc40da Mon Sep 17 00:00:00 2001 From: Jordan Niethe Date: Mon, 14 Dec 2020 22:14:09 +1100 Subject: [PATCH] Connect to the caravel logic analyzer This connects 32 read and 32 write bits to the caravel logic analyzer. Thanks to Jordan for the original patch --- Makefile | 2 +- fpga/top-caravel.vhdl | 55 ++++++++++++++++++++++++++++++++++++------- logic_analyzer.vhdl | 53 +++++++++++++++++++++++++++++++++++++++++ soc.vhdl | 1 + 4 files changed, 101 insertions(+), 10 deletions(-) create mode 100644 logic_analyzer.vhdl diff --git a/Makefile b/Makefile index a034b80..f9f4c26 100644 --- a/Makefile +++ b/Makefile @@ -52,7 +52,7 @@ core_files = decode_types.vhdl common.vhdl wishbone_types.vhdl fetch1.vhdl \ soc_files = $(core_files) wishbone_arbiter.vhdl wishbone_bram_wrapper.vhdl sync_fifo.vhdl \ wishbone_debug_master.vhdl xics.vhdl syscon.vhdl soc.vhdl \ - spi_rxtx.vhdl spi_flash_ctrl.vhdl + spi_rxtx.vhdl spi_flash_ctrl.vhdl logic_analyzer.vhdl uart_files = $(wildcard uart16550/*.v) diff --git a/fpga/top-caravel.vhdl b/fpga/top-caravel.vhdl index 2946532..f63c89d 100644 --- a/fpga/top-caravel.vhdl +++ b/fpga/top-caravel.vhdl @@ -21,7 +21,9 @@ entity toplevel is LOG_LENGTH : natural := 0; UART_IS_16550 : boolean := true; HAS_UART1 : boolean := false; - HAS_JTAG : boolean := true + HAS_JTAG : boolean := true; + INPUT_IOS : integer range 0 to 32 := 32; + OUTPUT_IOS : integer range 0 to 32 := 32 ); port( ext_clk : in std_ulogic; @@ -57,11 +59,12 @@ entity toplevel is ib_data : in std_ulogic_vector(7 downto 0); ib_pty : in std_ulogic; - -- Add an I/O pin to select fetching from flash on reset - alt_reset : in std_ulogic; + -- IO Signals + gpio_out : out std_ulogic_vector(OUTPUT_IOS-1 downto 0); + gpio_in : in std_ulogic_vector(INPUT_IOS-1 downto 0); - -- unused - wb_ext_io_out : out wb_io_slave_out + -- Add an I/O pin to select fetching from flash on reset + alt_reset : in std_ulogic ); end entity toplevel; @@ -83,13 +86,18 @@ architecture behaviour of toplevel is signal wb_mc_dat_i : wishbone_data_type; signal wb_mc_ack : std_ulogic; signal wb_mc_stall : std_ulogic; + + signal wb_logic_analyzer_out : wb_io_slave_out := wb_io_slave_out_init; + signal wb_logic_analyzer_in : wb_io_master_out; + + signal wb_ext_io_in : wb_io_master_out; + signal wb_ext_io_out : wb_io_slave_out; + signal wb_ext_is_eth : std_ulogic; + begin system_rst <= not ext_rst when RESET_LOW else ext_rst; - -- Unused, but tie it off - wb_ext_io_out <= wb_io_slave_out_init; - -- Main SoC soc0: entity work.soc generic map( @@ -110,7 +118,8 @@ begin LOG_LENGTH => LOG_LENGTH, UART0_IS_16550 => UART_IS_16550, HAS_UART1 => HAS_UART1, - HAS_JTAG => HAS_JTAG + HAS_JTAG => HAS_JTAG, + HAS_LITEETH => true ) port map ( -- System signals @@ -143,6 +152,10 @@ begin wb_dram_in => wb_dram_out, wb_dram_out => wb_dram_in, + wb_ext_io_in => wb_ext_io_in, + wb_ext_io_out => wb_ext_io_out, + wb_ext_is_eth => wb_ext_is_eth, + -- Reset PC to flash offset 0 (ie 0xf000000) alt_reset => alt_reset ); @@ -180,6 +193,30 @@ begin -- int => ob int ); + logic_analyzer: entity work.logic_analyzer + generic map( + INPUT_IOS => INPUT_IOS, + OUTPUT_IOS => OUTPUT_IOS + ) + port map( + clk => ext_clk, + rst => system_rst, + wb_in => wb_logic_analyzer_in, + wb_out => wb_logic_analyzer_out, + io_in => gpio_in, + io_out => gpio_out + ); + + wb_logic_analyzer_in.adr <= wb_ext_io_in.adr; + wb_logic_analyzer_in.dat <= wb_ext_io_in.dat; + wb_logic_analyzer_in.cyc <= wb_ext_io_in.cyc and wb_ext_is_eth; + wb_logic_analyzer_in.stb <= wb_ext_io_in.stb; + wb_logic_analyzer_in.sel <= wb_ext_io_in.sel; + wb_logic_analyzer_in.we <= wb_ext_io_in.we; + + wb_ext_io_out <= wb_logic_analyzer_out; + + -- External bus wishbone wb_mc_adr <= wb_dram_out.adr; wb_mc_dat_o <= wb_dram_out.dat; diff --git a/logic_analyzer.vhdl b/logic_analyzer.vhdl new file mode 100644 index 0000000..5f0eb4d --- /dev/null +++ b/logic_analyzer.vhdl @@ -0,0 +1,53 @@ +library ieee; +use ieee.std_logic_1164.all; + +library work; +use work.common.all; +use work.wishbone_types.all; + +entity logic_analyzer is + generic ( + INPUT_IOS : integer range 0 to 32; + OUTPUT_IOS : integer range 0 to 32 + ); + port ( + clk : in std_ulogic; + rst : in std_ulogic; + wb_in : in wb_io_master_out; + wb_out : out wb_io_slave_out; + io_in : in std_ulogic_vector(INPUT_IOS-1 downto 0); + io_out : out std_ulogic_vector(OUTPUT_IOS-1 downto 0) + ); +end logic_analyzer; + +architecture rtl of logic_analyzer is + signal we: std_ulogic; + signal re: std_ulogic; + signal ack: std_ulogic; +begin + -- Wishbone interface + we <= wb_in.stb and wb_in.cyc and wb_in.we; + re <= wb_in.stb and wb_in.cyc and not wb_in.we; + wb_out.stall <= '0'; + wb_out.ack <= ack; + + wb_0: process(clk) + begin + if rising_edge(clk) then + if rst = '1' then + io_out <= (others => '0'); + ack <= '0'; + else + if re = '1' then + wb_out.dat(INPUT_IOS-1 downto 0) <= io_in; + ack <= '1'; + elsif we = '1' then + io_out <= wb_in.dat(INPUT_IOS-1 downto 0); + ack <= '1'; + else + ack <= '0'; + end if; + end if; + end if; + end process; +end architecture rtl; diff --git a/soc.vhdl b/soc.vhdl index fee5124..9a461f8 100644 --- a/soc.vhdl +++ b/soc.vhdl @@ -30,6 +30,7 @@ use work.wishbone_types.all; -- External IO bus: -- 0xc8000000: LiteDRAM control (CSRs) +-- We will put the gpios here ... -- 0xc8020000: LiteEth CSRs (*) -- 0xc8030000: LiteEth MMIO (*)