OpenCores
URL https://opencores.org/ocsvn/neorv32/neorv32/trunk

Subversion Repositories neorv32

[/] [neorv32/] [trunk/] [rtl/] [core/] [neorv32_top.vhd] - Diff between revs 59 and 60

Go to most recent revision | Show entire file | Details | Blame | View Log

Rev 59 Rev 60
Line 56... Line 56...
    -- On-Chip Debugger (OCD) --
    -- On-Chip Debugger (OCD) --
    ON_CHIP_DEBUGGER_EN          : boolean := false;  -- implement on-chip debugger
    ON_CHIP_DEBUGGER_EN          : boolean := false;  -- implement on-chip debugger
 
 
    -- RISC-V CPU Extensions --
    -- RISC-V CPU Extensions --
    CPU_EXTENSION_RISCV_A        : boolean := false;  -- implement atomic extension?
    CPU_EXTENSION_RISCV_A        : boolean := false;  -- implement atomic extension?
    CPU_EXTENSION_RISCV_B        : boolean := false;  -- implement bit manipulation extensions?
 
    CPU_EXTENSION_RISCV_C        : boolean := false;  -- implement compressed extension?
    CPU_EXTENSION_RISCV_C        : boolean := false;  -- implement compressed extension?
    CPU_EXTENSION_RISCV_E        : boolean := false;  -- implement embedded RF extension?
    CPU_EXTENSION_RISCV_E        : boolean := false;  -- implement embedded RF extension?
    CPU_EXTENSION_RISCV_M        : boolean := false;  -- implement muld/div extension?
    CPU_EXTENSION_RISCV_M        : boolean := false;  -- implement muld/div extension?
    CPU_EXTENSION_RISCV_U        : boolean := false;  -- implement user mode extension?
    CPU_EXTENSION_RISCV_U        : boolean := false;  -- implement user mode extension?
    CPU_EXTENSION_RISCV_Zfinx    : boolean := false;  -- implement 32-bit floating-point extension (using INT regs!)
    CPU_EXTENSION_RISCV_Zfinx    : boolean := false;  -- implement 32-bit floating-point extension (using INT regs!)
Line 77... Line 76...
    PMP_NUM_REGIONS              : natural := 0;      -- number of regions (0..64)
    PMP_NUM_REGIONS              : natural := 0;      -- number of regions (0..64)
    PMP_MIN_GRANULARITY          : natural := 64*1024; -- minimal region granularity in bytes, has to be a power of 2, min 8 bytes
    PMP_MIN_GRANULARITY          : natural := 64*1024; -- minimal region granularity in bytes, has to be a power of 2, min 8 bytes
 
 
    -- Hardware Performance Monitors (HPM) --
    -- Hardware Performance Monitors (HPM) --
    HPM_NUM_CNTS                 : natural := 0;      -- number of implemented HPM counters (0..29)
    HPM_NUM_CNTS                 : natural := 0;      -- number of implemented HPM counters (0..29)
    HPM_CNT_WIDTH                : natural := 40;     -- total size of HPM counters (1..64)
    HPM_CNT_WIDTH                : natural := 40;     -- total size of HPM counters (0..64)
 
 
    -- Internal Instruction memory --
    -- Internal Instruction memory --
    MEM_INT_IMEM_EN              : boolean := true;   -- implement processor-internal instruction memory
    MEM_INT_IMEM_EN              : boolean := true;   -- implement processor-internal instruction memory
    MEM_INT_IMEM_SIZE            : natural := 16*1024; -- size of processor-internal instruction memory in bytes
    MEM_INT_IMEM_SIZE            : natural := 16*1024; -- size of processor-internal instruction memory in bytes
    MEM_INT_IMEM_ROM             : boolean := false;  -- implement processor-internal instruction memory as ROM
    MEM_INT_IMEM_ROM             : boolean := false;  -- implement processor-internal instruction memory as ROM
Line 105... Line 104...
    IO_MTIME_EN                  : boolean := true;   -- implement machine system timer (MTIME)?
    IO_MTIME_EN                  : boolean := true;   -- implement machine system timer (MTIME)?
    IO_UART0_EN                  : boolean := true;   -- implement primary universal asynchronous receiver/transmitter (UART0)?
    IO_UART0_EN                  : boolean := true;   -- implement primary universal asynchronous receiver/transmitter (UART0)?
    IO_UART1_EN                  : boolean := true;   -- implement secondary universal asynchronous receiver/transmitter (UART1)?
    IO_UART1_EN                  : boolean := true;   -- implement secondary universal asynchronous receiver/transmitter (UART1)?
    IO_SPI_EN                    : boolean := true;   -- implement serial peripheral interface (SPI)?
    IO_SPI_EN                    : boolean := true;   -- implement serial peripheral interface (SPI)?
    IO_TWI_EN                    : boolean := true;   -- implement two-wire interface (TWI)?
    IO_TWI_EN                    : boolean := true;   -- implement two-wire interface (TWI)?
    IO_PWM_EN                    : boolean := true;   -- implement pulse-width modulation unit (PWM)?
    IO_PWM_NUM_CH                : natural := 4;      -- number of PWM channels to implement (0..60); 0 = disabled
    IO_WDT_EN                    : boolean := true;   -- implement watch dog timer (WDT)?
    IO_WDT_EN                    : boolean := true;   -- implement watch dog timer (WDT)?
    IO_TRNG_EN                   : boolean := false;  -- implement true random number generator (TRNG)?
    IO_TRNG_EN                   : boolean := false;  -- implement true random number generator (TRNG)?
    IO_CFS_EN                    : boolean := false;  -- implement custom functions subsystem (CFS)?
    IO_CFS_EN                    : boolean := false;  -- implement custom functions subsystem (CFS)?
    IO_CFS_CONFIG                : std_ulogic_vector(31 downto 0) := x"00000000"; -- custom CFS configuration generic
    IO_CFS_CONFIG                : std_ulogic_vector(31 downto 0) := x"00000000"; -- custom CFS configuration generic
    IO_CFS_IN_SIZE               : positive := 32;    -- size of CFS input conduit in bits
    IO_CFS_IN_SIZE               : positive := 32;    -- size of CFS input conduit in bits
Line 170... Line 169...
 
 
    -- TWI (available if IO_TWI_EN = true) --
    -- TWI (available if IO_TWI_EN = true) --
    twi_sda_io  : inout std_logic; -- twi serial data line
    twi_sda_io  : inout std_logic; -- twi serial data line
    twi_scl_io  : inout std_logic; -- twi serial clock line
    twi_scl_io  : inout std_logic; -- twi serial clock line
 
 
    -- PWM (available if IO_PWM_EN = true) --
    -- PWM (available if IO_PWM_NUM_CH > 0) --
    pwm_o       : out std_ulogic_vector(03 downto 0); -- pwm channels
    pwm_o       : out std_ulogic_vector(IO_PWM_NUM_CH-1 downto 0); -- pwm channels
 
 
    -- Custom Functions Subsystem IO (available if IO_CFS_EN = true) --
    -- Custom Functions Subsystem IO (available if IO_CFS_EN = true) --
    cfs_in_i    : in  std_ulogic_vector(IO_CFS_IN_SIZE-1  downto 0); -- custom CFS inputs conduit
    cfs_in_i    : in  std_ulogic_vector(IO_CFS_IN_SIZE-1  downto 0); -- custom CFS inputs conduit
    cfs_out_o   : out std_ulogic_vector(IO_CFS_OUT_SIZE-1 downto 0); -- custom CFS outputs conduit
    cfs_out_o   : out std_ulogic_vector(IO_CFS_OUT_SIZE-1 downto 0); -- custom CFS outputs conduit
 
 
Line 206... Line 205...
  -- alignment check for internal memories --
  -- alignment check for internal memories --
  constant imem_align_check_c : std_ulogic_vector(index_size_f(MEM_INT_IMEM_SIZE)-1 downto 0) := (others => '0');
  constant imem_align_check_c : std_ulogic_vector(index_size_f(MEM_INT_IMEM_SIZE)-1 downto 0) := (others => '0');
  constant dmem_align_check_c : std_ulogic_vector(index_size_f(MEM_INT_DMEM_SIZE)-1 downto 0) := (others => '0');
  constant dmem_align_check_c : std_ulogic_vector(index_size_f(MEM_INT_DMEM_SIZE)-1 downto 0) := (others => '0');
 
 
  -- reset generator --
  -- reset generator --
  signal rstn_i_sync0 : std_ulogic;
  signal rstn_gen : std_ulogic_vector(7 downto 0);
  signal rstn_i_sync1 : std_ulogic;
 
  signal rstn_i_sync2 : std_ulogic;
 
  signal rstn_gen     : std_ulogic_vector(3 downto 0);
 
  signal ext_rstn     : std_ulogic;
  signal ext_rstn     : std_ulogic;
  signal sys_rstn     : std_ulogic;
  signal sys_rstn     : std_ulogic;
  signal wdt_rstn     : std_ulogic;
  signal wdt_rstn     : std_ulogic;
 
 
  -- clock generator --
  -- clock generator --
Line 271... Line 267...
  -- io space access --
  -- io space access --
  signal io_acc  : std_ulogic;
  signal io_acc  : std_ulogic;
  signal io_rden : std_ulogic;
  signal io_rden : std_ulogic;
  signal io_wren : std_ulogic;
  signal io_wren : std_ulogic;
 
 
  -- read-back buses -
  -- module response bus - entry type --
  signal imem_rdata     : std_ulogic_vector(data_width_c-1 downto 0);
  type resp_bus_entry_t is record
  signal imem_ack       : std_ulogic;
    rdata : std_ulogic_vector(data_width_c-1 downto 0);
  signal dmem_rdata     : std_ulogic_vector(data_width_c-1 downto 0);
    ack   : std_ulogic;
  signal dmem_ack       : std_ulogic;
    err   : std_ulogic;
  signal bootrom_rdata  : std_ulogic_vector(data_width_c-1 downto 0);
  end record;
  signal bootrom_ack    : std_ulogic;
  constant resp_bus_entry_terminate_c : resp_bus_entry_t := (rdata => (others => '0'), ack => '0', err => '0');
  signal wishbone_rdata : std_ulogic_vector(data_width_c-1 downto 0);
 
  signal wishbone_ack   : std_ulogic;
  -- module response bus - device ID --
  signal wishbone_err   : std_ulogic;
  type resp_bus_id_t is (RESP_IMEM, RESP_DMEM, RESP_BOOTROM, RESP_WISHBONE, RESP_GPIO, RESP_MTIME, RESP_UART0, RESP_UART1, RESP_SPI,
  signal gpio_rdata     : std_ulogic_vector(data_width_c-1 downto 0);
                         RESP_TWI, RESP_PWM, RESP_WDT, RESP_TRNG, RESP_CFS, RESP_NCO, RESP_NEOLED, RESP_SYSINFO, RESP_OCD);
  signal gpio_ack       : std_ulogic;
 
  signal mtime_rdata    : std_ulogic_vector(data_width_c-1 downto 0);
  -- module response bus --
  signal mtime_ack      : std_ulogic;
  type resp_bus_t is array (resp_bus_id_t) of resp_bus_entry_t;
  signal uart0_rdata    : std_ulogic_vector(data_width_c-1 downto 0);
  signal resp_bus : resp_bus_t := (others => resp_bus_entry_terminate_c);
  signal uart0_ack      : std_ulogic;
 
  signal uart1_rdata    : std_ulogic_vector(data_width_c-1 downto 0);
 
  signal uart1_ack      : std_ulogic;
 
  signal spi_rdata      : std_ulogic_vector(data_width_c-1 downto 0);
 
  signal spi_ack        : std_ulogic;
 
  signal twi_rdata      : std_ulogic_vector(data_width_c-1 downto 0);
 
  signal twi_ack        : std_ulogic;
 
  signal pwm_rdata      : std_ulogic_vector(data_width_c-1 downto 0);
 
  signal pwm_ack        : std_ulogic;
 
  signal wdt_rdata      : std_ulogic_vector(data_width_c-1 downto 0);
 
  signal wdt_ack        : std_ulogic;
 
  signal trng_rdata     : std_ulogic_vector(data_width_c-1 downto 0);
 
  signal trng_ack       : std_ulogic;
 
  signal cfs_rdata      : std_ulogic_vector(data_width_c-1 downto 0);
 
  signal cfs_ack        : std_ulogic;
 
  signal nco_rdata      : std_ulogic_vector(data_width_c-1 downto 0);
 
  signal nco_ack        : std_ulogic;
 
  signal neoled_rdata   : std_ulogic_vector(data_width_c-1 downto 0);
 
  signal neoled_ack     : std_ulogic;
 
  signal sysinfo_rdata  : std_ulogic_vector(data_width_c-1 downto 0);
 
  signal sysinfo_ack    : std_ulogic;
 
  signal bus_keeper_err : std_ulogic;
 
  signal dm_rdata       : std_ulogic_vector(data_width_c-1 downto 0);
 
  signal dm_ack         : std_ulogic;
 
 
 
  -- IRQs --
  -- IRQs --
  signal mtime_irq     : std_ulogic;
 
  --
 
  signal fast_irq      : std_ulogic_vector(15 downto 0);
  signal fast_irq      : std_ulogic_vector(15 downto 0);
  signal fast_irq_ack  : std_ulogic_vector(15 downto 0);
  signal fast_irq_ack  : std_ulogic_vector(15 downto 0);
  --
  signal mtime_irq     : std_ulogic;
  signal gpio_irq      : std_ulogic;
  signal gpio_irq      : std_ulogic;
  signal wdt_irq       : std_ulogic;
  signal wdt_irq       : std_ulogic;
  signal uart0_rxd_irq : std_ulogic;
  signal uart0_rxd_irq : std_ulogic;
  signal uart0_txd_irq : std_ulogic;
  signal uart0_txd_irq : std_ulogic;
  signal uart1_rxd_irq : std_ulogic;
  signal uart1_rxd_irq : std_ulogic;
Line 332... Line 302...
  signal neoled_irq    : std_ulogic;
  signal neoled_irq    : std_ulogic;
 
 
  -- misc --
  -- misc --
  signal mtime_time : std_ulogic_vector(63 downto 0); -- current system time from MTIME
  signal mtime_time : std_ulogic_vector(63 downto 0); -- current system time from MTIME
  signal cpu_sleep  : std_ulogic; -- CPU is in sleep mode when set
  signal cpu_sleep  : std_ulogic; -- CPU is in sleep mode when set
 
  signal bus_keeper_err : std_ulogic; -- bus keeper: bus access timeout
 
 
begin
begin
 
 
  -- Sanity Checks --------------------------------------------------------------------------
  -- Sanity Checks --------------------------------------------------------------------------
  -- -------------------------------------------------------------------------------------------
  -- -------------------------------------------------------------------------------------------
Line 364... Line 335...
  assert not (ON_CHIP_DEBUGGER_EN = true) report "NEORV32 PROCESSOR CONFIG NOTE. Implementing on-chip debugger (OCD)." severity note;
  assert not (ON_CHIP_DEBUGGER_EN = true) report "NEORV32 PROCESSOR CONFIG NOTE. Implementing on-chip debugger (OCD)." severity note;
 
 
 
 
  -- Reset Generator ------------------------------------------------------------------------
  -- Reset Generator ------------------------------------------------------------------------
  -- -------------------------------------------------------------------------------------------
  -- -------------------------------------------------------------------------------------------
  reset_generator_sync: process(clk_i)
  reset_generator: process(rstn_i, clk_i)
  begin
  begin
    -- make sure the external reset is free of metastability and has a minimal duration of 1 clock cycle
    if (rstn_i = '0') then
    if rising_edge(clk_i) then
 
      rstn_i_sync0 <= rstn_i;
 
      rstn_i_sync1 <= rstn_i_sync0;
 
      rstn_i_sync2 <= rstn_i_sync1;
 
    end if;
 
  end process reset_generator_sync;
 
 
 
  -- keep internal reset active for at least 4 clock cycles
 
  reset_generator: process(rstn_i_sync1, rstn_i_sync2, clk_i)
 
  begin
 
    if ((rstn_i_sync1 and rstn_i_sync2) = '0') then -- signal stable?
 
      rstn_gen <= (others => '0');
      rstn_gen <= (others => '0');
 
      sys_rstn <= '0';
    elsif rising_edge(clk_i) then
    elsif rising_edge(clk_i) then
 
      -- keep internal reset active for at least <rstn_gen'size> clock cycles --
      rstn_gen <= rstn_gen(rstn_gen'left-1 downto 0) & '1';
      rstn_gen <= rstn_gen(rstn_gen'left-1 downto 0) & '1';
 
      -- system reset: can also be triggered by watchdog and debug module --
 
      sys_rstn <= ext_rstn and wdt_rstn and dci_ndmrstn;
    end if;
    end if;
  end process reset_generator;
  end process reset_generator;
 
 
  ext_rstn <= rstn_gen(rstn_gen'left); -- the beautified external reset signal
  -- beautified external reset signal --
 
  ext_rstn <= rstn_gen(rstn_gen'left);
  -- internal reset buffer --
 
  soc_reset_generator: process(clk_i)
 
  begin
 
    if rising_edge(clk_i) then
 
      sys_rstn <= ext_rstn and wdt_rstn and dci_ndmrstn; -- system reset: can also be triggered by watchdog and debug module
 
    end if;
 
  end process soc_reset_generator;
 
 
 
 
 
  -- Clock Generator ------------------------------------------------------------------------
  -- Clock Generator ------------------------------------------------------------------------
  -- -------------------------------------------------------------------------------------------
  -- -------------------------------------------------------------------------------------------
  clock_generator: process(sys_rstn, clk_i)
  clock_generator: process(sys_rstn, clk_i)
  begin
  begin
    if (sys_rstn = '0') then
    if (sys_rstn = '0') then
 
      clk_gen_en <= (others => '-');
      clk_div    <= (others => '0');
      clk_div    <= (others => '0');
      clk_div_ff <= (others => '0');
      clk_div_ff <= (others => '-');
      clk_gen_en <= (others => '0');
      clk_gen    <= (others => '-');
    elsif rising_edge(clk_i) then
    elsif rising_edge(clk_i) then
      -- fresh clocks anyone? --
      -- fresh clocks anyone? --
      clk_gen_en(0) <= wdt_cg_en;
      clk_gen_en(0) <= wdt_cg_en;
      clk_gen_en(1) <= uart0_cg_en;
      clk_gen_en(1) <= uart0_cg_en;
      clk_gen_en(2) <= uart1_cg_en;
      clk_gen_en(2) <= uart1_cg_en;
Line 414... Line 372...
      clk_gen_en(4) <= twi_cg_en;
      clk_gen_en(4) <= twi_cg_en;
      clk_gen_en(5) <= pwm_cg_en;
      clk_gen_en(5) <= pwm_cg_en;
      clk_gen_en(6) <= cfs_cg_en;
      clk_gen_en(6) <= cfs_cg_en;
      clk_gen_en(7) <= nco_cg_en;
      clk_gen_en(7) <= nco_cg_en;
      clk_gen_en(8) <= neoled_cg_en;
      clk_gen_en(8) <= neoled_cg_en;
      if (or_all_f(clk_gen_en) = '1') then
      -- actual clock generator --
 
      if (or_reduce_f(clk_gen_en) = '1') then
        clk_div <= std_ulogic_vector(unsigned(clk_div) + 1);
        clk_div <= std_ulogic_vector(unsigned(clk_div) + 1);
      end if;
      end if;
      clk_div_ff <= clk_div;
 
    end if;
 
  end process clock_generator;
 
 
 
  -- clock enables: rising edge detectors --
  -- clock enables: rising edge detectors --
  clock_generator_edge: process(clk_i)
      clk_div_ff <= clk_div;
  begin
 
    if rising_edge(clk_i) then
 
      clk_gen(clk_div2_c)    <= clk_div(0)  and (not clk_div_ff(0));  -- CLK/2
      clk_gen(clk_div2_c)    <= clk_div(0)  and (not clk_div_ff(0));  -- CLK/2
      clk_gen(clk_div4_c)    <= clk_div(1)  and (not clk_div_ff(1));  -- CLK/4
      clk_gen(clk_div4_c)    <= clk_div(1)  and (not clk_div_ff(1));  -- CLK/4
      clk_gen(clk_div8_c)    <= clk_div(2)  and (not clk_div_ff(2));  -- CLK/8
      clk_gen(clk_div8_c)    <= clk_div(2)  and (not clk_div_ff(2));  -- CLK/8
      clk_gen(clk_div64_c)   <= clk_div(5)  and (not clk_div_ff(5));  -- CLK/64
      clk_gen(clk_div64_c)   <= clk_div(5)  and (not clk_div_ff(5));  -- CLK/64
      clk_gen(clk_div128_c)  <= clk_div(6)  and (not clk_div_ff(6));  -- CLK/128
      clk_gen(clk_div128_c)  <= clk_div(6)  and (not clk_div_ff(6));  -- CLK/128
      clk_gen(clk_div1024_c) <= clk_div(9)  and (not clk_div_ff(9));  -- CLK/1024
      clk_gen(clk_div1024_c) <= clk_div(9)  and (not clk_div_ff(9));  -- CLK/1024
      clk_gen(clk_div2048_c) <= clk_div(10) and (not clk_div_ff(10)); -- CLK/2048
      clk_gen(clk_div2048_c) <= clk_div(10) and (not clk_div_ff(10)); -- CLK/2048
      clk_gen(clk_div4096_c) <= clk_div(11) and (not clk_div_ff(11)); -- CLK/4096
      clk_gen(clk_div4096_c) <= clk_div(11) and (not clk_div_ff(11)); -- CLK/4096
    end if;
    end if;
  end process clock_generator_edge;
  end process clock_generator;
 
 
 
 
  -- CPU Core -------------------------------------------------------------------------------
  -- CPU Core -------------------------------------------------------------------------------
  -- -------------------------------------------------------------------------------------------
  -- -------------------------------------------------------------------------------------------
  neorv32_cpu_inst: neorv32_cpu
  neorv32_cpu_inst: neorv32_cpu
Line 447... Line 400...
    HW_THREAD_ID                 => HW_THREAD_ID,        -- hardware thread id
    HW_THREAD_ID                 => HW_THREAD_ID,        -- hardware thread id
    CPU_BOOT_ADDR                => cpu_boot_addr_c,     -- cpu boot address
    CPU_BOOT_ADDR                => cpu_boot_addr_c,     -- cpu boot address
    CPU_DEBUG_ADDR               => dm_base_c,           -- cpu debug mode start address
    CPU_DEBUG_ADDR               => dm_base_c,           -- cpu debug mode start address
    -- RISC-V CPU Extensions --
    -- RISC-V CPU Extensions --
    CPU_EXTENSION_RISCV_A        => CPU_EXTENSION_RISCV_A,        -- implement atomic extension?
    CPU_EXTENSION_RISCV_A        => CPU_EXTENSION_RISCV_A,        -- implement atomic extension?
    CPU_EXTENSION_RISCV_B        => CPU_EXTENSION_RISCV_B,        -- implement bit manipulation extensions?
 
    CPU_EXTENSION_RISCV_C        => CPU_EXTENSION_RISCV_C,        -- implement compressed extension?
    CPU_EXTENSION_RISCV_C        => CPU_EXTENSION_RISCV_C,        -- implement compressed extension?
    CPU_EXTENSION_RISCV_E        => CPU_EXTENSION_RISCV_E,        -- implement embedded RF extension?
    CPU_EXTENSION_RISCV_E        => CPU_EXTENSION_RISCV_E,        -- implement embedded RF extension?
    CPU_EXTENSION_RISCV_M        => CPU_EXTENSION_RISCV_M,        -- implement muld/div extension?
    CPU_EXTENSION_RISCV_M        => CPU_EXTENSION_RISCV_M,        -- implement muld/div extension?
    CPU_EXTENSION_RISCV_U        => CPU_EXTENSION_RISCV_U,        -- implement user mode extension?
    CPU_EXTENSION_RISCV_U        => CPU_EXTENSION_RISCV_U,        -- implement user mode extension?
    CPU_EXTENSION_RISCV_Zfinx    => CPU_EXTENSION_RISCV_Zfinx,    -- implement 32-bit floating-point extension (using INT reg!)
    CPU_EXTENSION_RISCV_Zfinx    => CPU_EXTENSION_RISCV_Zfinx,    -- implement 32-bit floating-point extension (using INT reg!)
Line 465... Line 417...
    -- Physical Memory Protection (PMP) --
    -- Physical Memory Protection (PMP) --
    PMP_NUM_REGIONS              => PMP_NUM_REGIONS,     -- number of regions (0..64)
    PMP_NUM_REGIONS              => PMP_NUM_REGIONS,     -- number of regions (0..64)
    PMP_MIN_GRANULARITY          => PMP_MIN_GRANULARITY, -- minimal region granularity in bytes, has to be a power of 2, min 8 bytes
    PMP_MIN_GRANULARITY          => PMP_MIN_GRANULARITY, -- minimal region granularity in bytes, has to be a power of 2, min 8 bytes
    -- Hardware Performance Monitors (HPM) --
    -- Hardware Performance Monitors (HPM) --
    HPM_NUM_CNTS                 => HPM_NUM_CNTS,        -- number of implemented HPM counters (0..29)
    HPM_NUM_CNTS                 => HPM_NUM_CNTS,        -- number of implemented HPM counters (0..29)
    HPM_CNT_WIDTH                => HPM_CNT_WIDTH        -- total size of HPM counters (1..64)
    HPM_CNT_WIDTH                => HPM_CNT_WIDTH        -- total size of HPM counters (0..64)
  )
  )
  port map (
  port map (
    -- global control --
    -- global control --
    clk_i          => clk_i,        -- global clock, rising edge
    clk_i          => clk_i,        -- global clock, rising edge
    rstn_i         => sys_rstn,     -- global reset, low-active, async
    rstn_i         => sys_rstn,     -- global reset, low-active, async
Line 644... Line 596...
    p_bus_lock_o    => p_bus.lock,     -- exclusive access request
    p_bus_lock_o    => p_bus.lock,     -- exclusive access request
    p_bus_ack_i     => p_bus.ack,      -- bus transfer acknowledge
    p_bus_ack_i     => p_bus.ack,      -- bus transfer acknowledge
    p_bus_err_i     => p_bus.err       -- bus transfer error
    p_bus_err_i     => p_bus.err       -- bus transfer error
  );
  );
 
 
  -- static signals --
  -- current CPU privilege level --
  p_bus.priv <= cpu_i.priv; -- current CPU privilege level: cpu_i.priv == cpu_d.priv
  p_bus.priv <= cpu_i.priv; -- note: cpu_i.priv == cpu_d.priv
 
 
  -- processor bus: CPU transfer data input --
  -- fence operation (unused) --
  p_bus.rdata <= (imem_rdata or dmem_rdata or bootrom_rdata) or wishbone_rdata or (gpio_rdata or mtime_rdata or uart0_rdata or uart1_rdata or
  p_bus.fence <= cpu_d.fence or cpu_i.fence;
                 spi_rdata or twi_rdata or pwm_rdata or wdt_rdata or trng_rdata or cfs_rdata or nco_rdata or neoled_rdata or  sysinfo_rdata) or dm_rdata;
 
 
 
  -- processor bus: CPU transfer ACK input --
 
  p_bus.ack <= (imem_ack or dmem_ack or bootrom_ack) or wishbone_ack or (gpio_ack or mtime_ack or uart0_ack or uart1_ack or
 
               spi_ack or twi_ack or pwm_ack or wdt_ack or trng_ack or cfs_ack or nco_ack or neoled_ack or sysinfo_ack) or dm_ack;
 
 
 
  -- processor bus: CPU transfer data bus error input --
  -- bus response --
  p_bus.err <= bus_keeper_err or wishbone_err;
  bus_response: process(resp_bus, bus_keeper_err)
 
    variable rdata_v : std_ulogic_vector(data_width_c-1 downto 0);
 
    variable ack_v   : std_ulogic;
 
    variable err_v   : std_ulogic;
 
  begin
 
    rdata_v := (others => '0');
 
    ack_v   := '0';
 
    err_v   := '0';
 
    for i in resp_bus'range loop
 
      rdata_v := rdata_v or resp_bus(i).rdata; -- read data
 
      ack_v   := ack_v   or resp_bus(i).ack;   -- acknowledge
 
      err_v   := err_v   or resp_bus(i).err;   -- error
 
    end loop; -- i
 
    p_bus.rdata <= rdata_v; -- processor bus: CPU transfer data input
 
    p_bus.ack   <= ack_v;   -- processor bus: CPU transfer ACK input
 
    p_bus.err   <= err_v or bus_keeper_err; -- processor bus: CPU transfer data bus error input
 
  end process;
 
 
 
 
  -- Processor-Internal Bus Keeper (BUS_KEEPER) ---------------------------------------------
  -- Processor-Internal Bus Keeper (BUS_KEEPER) ---------------------------------------------
  -- -------------------------------------------------------------------------------------------
  -- -------------------------------------------------------------------------------------------
  neorv32_bus_keeper_inst: neorv32_bus_keeper
  neorv32_bus_keeper_inst: neorv32_bus_keeper
Line 703... Line 666...
      rden_i => p_bus.re,    -- read enable
      rden_i => p_bus.re,    -- read enable
      wren_i => p_bus.we,    -- write enable
      wren_i => p_bus.we,    -- write enable
      ben_i  => p_bus.ben,   -- byte write enable
      ben_i  => p_bus.ben,   -- byte write enable
      addr_i => p_bus.addr,  -- address
      addr_i => p_bus.addr,  -- address
      data_i => p_bus.wdata, -- data in
      data_i => p_bus.wdata, -- data in
      data_o => imem_rdata,  -- data out
      data_o => resp_bus(RESP_IMEM).rdata, -- data out
      ack_o  => imem_ack     -- transfer acknowledge
      ack_o  => resp_bus(RESP_IMEM).ack    -- transfer acknowledge
    );
    );
 
    resp_bus(RESP_IMEM).err <= '0'; -- no access error possible
  end generate;
  end generate;
 
 
  neorv32_int_imem_inst_false:
  neorv32_int_imem_inst_false:
  if (MEM_INT_IMEM_EN = false) generate
  if (MEM_INT_IMEM_EN = false) generate
    imem_rdata <= (others => '0');
    resp_bus(RESP_IMEM) <= resp_bus_entry_terminate_c;
    imem_ack   <= '0';
 
  end generate;
  end generate;
 
 
 
 
  -- Processor-Internal Data Memory (DMEM) --------------------------------------------------
  -- Processor-Internal Data Memory (DMEM) --------------------------------------------------
  -- -------------------------------------------------------------------------------------------
  -- -------------------------------------------------------------------------------------------
Line 731... Line 694...
      rden_i => p_bus.re,    -- read enable
      rden_i => p_bus.re,    -- read enable
      wren_i => p_bus.we,    -- write enable
      wren_i => p_bus.we,    -- write enable
      ben_i  => p_bus.ben,   -- byte write enable
      ben_i  => p_bus.ben,   -- byte write enable
      addr_i => p_bus.addr,  -- address
      addr_i => p_bus.addr,  -- address
      data_i => p_bus.wdata, -- data in
      data_i => p_bus.wdata, -- data in
      data_o => dmem_rdata,  -- data out
      data_o => resp_bus(RESP_DMEM).rdata, -- data out
      ack_o  => dmem_ack     -- transfer acknowledge
      ack_o  => resp_bus(RESP_DMEM).ack    -- transfer acknowledge
    );
    );
 
    resp_bus(RESP_DMEM).err <= '0'; -- no access error possible
  end generate;
  end generate;
 
 
  neorv32_int_dmem_inst_false:
  neorv32_int_dmem_inst_false:
  if (MEM_INT_DMEM_EN = false) generate
  if (MEM_INT_DMEM_EN = false) generate
    dmem_rdata <= (others => '0');
    resp_bus(RESP_DMEM) <= resp_bus_entry_terminate_c;
    dmem_ack   <= '0';
 
  end generate;
  end generate;
 
 
 
 
  -- Processor-Internal Bootloader ROM (BOOTROM) --------------------------------------------
  -- Processor-Internal Bootloader ROM (BOOTROM) --------------------------------------------
  -- -------------------------------------------------------------------------------------------
  -- -------------------------------------------------------------------------------------------
Line 756... Line 719...
    )
    )
    port map (
    port map (
      clk_i  => clk_i,         -- global clock line
      clk_i  => clk_i,         -- global clock line
      rden_i => p_bus.re,      -- read enable
      rden_i => p_bus.re,      -- read enable
      addr_i => p_bus.addr,    -- address
      addr_i => p_bus.addr,    -- address
      data_o => bootrom_rdata, -- data out
      data_o => resp_bus(RESP_BOOTROM).rdata, -- data out
      ack_o  => bootrom_ack    -- transfer acknowledge
      ack_o  => resp_bus(RESP_BOOTROM).ack    -- transfer acknowledge
    );
    );
 
    resp_bus(RESP_BOOTROM).err <= '0'; -- no access error possible
  end generate;
  end generate;
 
 
  neorv32_boot_rom_inst_false:
  neorv32_boot_rom_inst_false:
  if (BOOTLOADER_EN = false) generate
  if (BOOTLOADER_EN = false) generate
    bootrom_rdata <= (others => '0');
    resp_bus(RESP_BOOTROM) <= resp_bus_entry_terminate_c;
    bootrom_ack   <= '0';
 
  end generate;
  end generate;
 
 
 
 
  -- External Wishbone Gateway (WISHBONE) ---------------------------------------------------
  -- External Wishbone Gateway (WISHBONE) ---------------------------------------------------
  -- -------------------------------------------------------------------------------------------
  -- -------------------------------------------------------------------------------------------
Line 795... Line 758...
      addr_i    => p_bus.addr,     -- address
      addr_i    => p_bus.addr,     -- address
      rden_i    => p_bus.re,       -- read enable
      rden_i    => p_bus.re,       -- read enable
      wren_i    => p_bus.we,       -- write enable
      wren_i    => p_bus.we,       -- write enable
      ben_i     => p_bus.ben,      -- byte write enable
      ben_i     => p_bus.ben,      -- byte write enable
      data_i    => p_bus.wdata,    -- data in
      data_i    => p_bus.wdata,    -- data in
      data_o    => wishbone_rdata, -- data out
      data_o    => resp_bus(RESP_WISHBONE).rdata, -- data out
      lock_i    => p_bus.lock,     -- exclusive access request
      lock_i    => p_bus.lock,     -- exclusive access request
      ack_o     => wishbone_ack,   -- transfer acknowledge
      ack_o     => resp_bus(RESP_WISHBONE).ack,   -- transfer acknowledge
      err_o     => wishbone_err,   -- transfer error
      err_o     => resp_bus(RESP_WISHBONE).err,   -- transfer error
      priv_i    => p_bus.priv,     -- current CPU privilege level
      priv_i    => p_bus.priv,     -- current CPU privilege level
      -- wishbone interface --
      -- wishbone interface --
      wb_tag_o  => wb_tag_o,       -- request tag
      wb_tag_o  => wb_tag_o,       -- request tag
      wb_adr_o  => wb_adr_o,       -- address
      wb_adr_o  => wb_adr_o,       -- address
      wb_dat_i  => wb_dat_i,       -- read data
      wb_dat_i  => wb_dat_i,       -- read data
Line 817... Line 780...
    );
    );
  end generate;
  end generate;
 
 
  neorv32_wishbone_inst_false:
  neorv32_wishbone_inst_false:
  if (MEM_EXT_EN = false) generate
  if (MEM_EXT_EN = false) generate
    wishbone_rdata <= (others => '0');
    resp_bus(RESP_WISHBONE) <= resp_bus_entry_terminate_c;
    wishbone_ack   <= '0';
 
    wishbone_err   <= '0';
 
    --
    --
    wb_adr_o <= (others => '0');
    wb_adr_o <= (others => '0');
    wb_dat_o <= (others => '0');
    wb_dat_o <= (others => '0');
    wb_we_o  <= '0';
    wb_we_o  <= '0';
    wb_sel_o <= (others => '0');
    wb_sel_o <= (others => '0');
    wb_stb_o <= '0';
    wb_stb_o <= '0';
    wb_cyc_o <= '0';
    wb_cyc_o <= '0';
 
    wb_lock_o <= '0';
    wb_tag_o <= (others => '0');
    wb_tag_o <= (others => '0');
  end generate;
  end generate;
 
 
 
 
  -- IO Access? -----------------------------------------------------------------------------
  -- IO Access? -----------------------------------------------------------------------------
  -- -------------------------------------------------------------------------------------------
  -- -------------------------------------------------------------------------------------------
  io_acc  <= '1' when (p_bus.addr(data_width_c-1 downto index_size_f(io_size_c)) = io_base_c(data_width_c-1 downto index_size_f(io_size_c))) else '0';
  io_acc  <= '1' when (p_bus.addr(data_width_c-1 downto index_size_f(io_size_c)) = io_base_c(data_width_c-1 downto index_size_f(io_size_c))) else '0';
  io_rden <= io_acc and p_bus.re and (not p_bus.src); -- PMA: no_execute for IO region
  io_rden <= io_acc and p_bus.re and (not p_bus.src); -- PMA: no_execute for IO region
  -- the default NEORV32 peripheral/IO devices in the IO area can only be written in word mode (reduces HW complexity)
  -- the default NEORV32 peripheral/IO devices in the IO area can only be written in word mode (reduces HW complexity)
  io_wren <= io_acc and p_bus.we and and_all_f(p_bus.ben) and (not p_bus.src); -- PMA: write32 only, no_execute for IO region
  io_wren <= io_acc and p_bus.we and and_reduce_f(p_bus.ben) and (not p_bus.src); -- PMA: write32 only, no_execute for IO region
 
 
 
 
  -- Custom Functions Subsystem (CFS) -------------------------------------------------------
  -- Custom Functions Subsystem (CFS) -------------------------------------------------------
  -- -------------------------------------------------------------------------------------------
  -- -------------------------------------------------------------------------------------------
  neorv32_cfs_inst_true:
  neorv32_cfs_inst_true:
Line 857... Line 819...
      rstn_i      => sys_rstn,        -- global reset line, low-active, use as async
      rstn_i      => sys_rstn,        -- global reset line, low-active, use as async
      addr_i      => p_bus.addr,      -- address
      addr_i      => p_bus.addr,      -- address
      rden_i      => io_rden,         -- read enable
      rden_i      => io_rden,         -- read enable
      wren_i      => io_wren,         -- byte write enable
      wren_i      => io_wren,         -- byte write enable
      data_i      => p_bus.wdata,     -- data in
      data_i      => p_bus.wdata,     -- data in
      data_o      => cfs_rdata,       -- data out
      data_o      => resp_bus(RESP_CFS).rdata, -- data out
      ack_o       => cfs_ack,         -- transfer acknowledge
      ack_o       => resp_bus(RESP_CFS).ack,   -- transfer acknowledge
      -- clock generator --
      -- clock generator --
      clkgen_en_o => cfs_cg_en,       -- enable clock generator
      clkgen_en_o => cfs_cg_en,       -- enable clock generator
      clkgen_i    => clk_gen,         -- "clock" inputs
      clkgen_i    => clk_gen,         -- "clock" inputs
      -- CPU state --
      -- CPU state --
      sleep_i     => cpu_sleep,       -- set if cpu is in sleep mode
      sleep_i     => cpu_sleep,       -- set if cpu is in sleep mode
Line 871... Line 833...
      irq_ack_i   => cfs_irq_ack,     -- interrupt acknowledge
      irq_ack_i   => cfs_irq_ack,     -- interrupt acknowledge
      -- custom io (conduit) --
      -- custom io (conduit) --
      cfs_in_i    => cfs_in_i,        -- custom inputs
      cfs_in_i    => cfs_in_i,        -- custom inputs
      cfs_out_o   => cfs_out_o        -- custom outputs
      cfs_out_o   => cfs_out_o        -- custom outputs
    );
    );
 
    resp_bus(RESP_CFS).err <= '0'; -- no access error possible
  end generate;
  end generate;
 
 
  neorv32_cfs_inst_false:
  neorv32_cfs_inst_false:
  if (IO_CFS_EN = false) generate
  if (IO_CFS_EN = false) generate
    cfs_rdata <= (others => '0');
    resp_bus(RESP_CFS) <= resp_bus_entry_terminate_c;
    cfs_ack   <= '0';
 
    cfs_cg_en <= '0';
    cfs_cg_en <= '0';
    cfs_irq   <= '0';
    cfs_irq   <= '0';
    cfs_out_o <= (others => '0');
    cfs_out_o <= (others => '0');
  end generate;
  end generate;
 
 
Line 895... Line 857...
      clk_i  => clk_i,       -- global clock line
      clk_i  => clk_i,       -- global clock line
      addr_i => p_bus.addr,  -- address
      addr_i => p_bus.addr,  -- address
      rden_i => io_rden,     -- read enable
      rden_i => io_rden,     -- read enable
      wren_i => io_wren,     -- write enable
      wren_i => io_wren,     -- write enable
      data_i => p_bus.wdata, -- data in
      data_i => p_bus.wdata, -- data in
      data_o => gpio_rdata,  -- data out
      data_o => resp_bus(RESP_GPIO).rdata, -- data out
      ack_o  => gpio_ack,    -- transfer acknowledge
      ack_o  => resp_bus(RESP_GPIO).ack,   -- transfer acknowledge
      -- parallel io --
      -- parallel io --
      gpio_o => gpio_o,
      gpio_o => gpio_o,
      gpio_i => gpio_i,
      gpio_i => gpio_i,
      -- interrupt --
      -- interrupt --
      irq_o  => gpio_irq     -- pin-change interrupt
      irq_o  => gpio_irq     -- pin-change interrupt
    );
    );
 
    resp_bus(RESP_GPIO).err <= '0'; -- no access error possible
  end generate;
  end generate;
 
 
  neorv32_gpio_inst_false:
  neorv32_gpio_inst_false:
  if (IO_GPIO_EN = false) generate
  if (IO_GPIO_EN = false) generate
    gpio_rdata <= (others => '0');
    resp_bus(RESP_GPIO) <= resp_bus_entry_terminate_c;
    gpio_ack   <= '0';
 
    gpio_o     <= (others => '0');
    gpio_o     <= (others => '0');
    gpio_irq   <= '0';
    gpio_irq   <= '0';
  end generate;
  end generate;
 
 
 
 
Line 927... Line 889...
      rstn_i      => ext_rstn,    -- global reset line, low-active
      rstn_i      => ext_rstn,    -- global reset line, low-active
      rden_i      => io_rden,     -- read enable
      rden_i      => io_rden,     -- read enable
      wren_i      => io_wren,     -- write enable
      wren_i      => io_wren,     -- write enable
      addr_i      => p_bus.addr,  -- address
      addr_i      => p_bus.addr,  -- address
      data_i      => p_bus.wdata, -- data in
      data_i      => p_bus.wdata, -- data in
      data_o      => wdt_rdata,   -- data out
      data_o      => resp_bus(RESP_WDT).rdata, -- data out
      ack_o       => wdt_ack,     -- transfer acknowledge
      ack_o       => resp_bus(RESP_WDT).ack,   -- transfer acknowledge
      -- clock generator --
      -- clock generator --
      clkgen_en_o => wdt_cg_en,   -- enable clock generator
      clkgen_en_o => wdt_cg_en,   -- enable clock generator
      clkgen_i    => clk_gen,
      clkgen_i    => clk_gen,
      -- timeout event --
      -- timeout event --
      irq_o       => wdt_irq,     -- timeout IRQ
      irq_o       => wdt_irq,     -- timeout IRQ
      rstn_o      => wdt_rstn     -- timeout reset, low_active, use it as async!
      rstn_o      => wdt_rstn     -- timeout reset, low_active, use it as async!
    );
    );
 
    resp_bus(RESP_WDT).err <= '0'; -- no access error possible
  end generate;
  end generate;
 
 
  neorv32_wdt_inst_false:
  neorv32_wdt_inst_false:
  if (IO_WDT_EN = false) generate
  if (IO_WDT_EN = false) generate
    wdt_rdata <= (others => '0');
    resp_bus(RESP_WDT) <= resp_bus_entry_terminate_c;
    wdt_ack   <= '0';
 
    wdt_irq   <= '0';
    wdt_irq   <= '0';
    wdt_rstn  <= '1';
    wdt_rstn  <= '1';
    wdt_cg_en <= '0';
    wdt_cg_en <= '0';
  end generate;
  end generate;
 
 
Line 956... Line 918...
  if (IO_MTIME_EN = true) generate
  if (IO_MTIME_EN = true) generate
    neorv32_mtime_inst: neorv32_mtime
    neorv32_mtime_inst: neorv32_mtime
    port map (
    port map (
      -- host access --
      -- host access --
      clk_i     => clk_i,       -- global clock line
      clk_i     => clk_i,       -- global clock line
      rstn_i    => sys_rstn,    -- global reset, low-active, async
 
      addr_i    => p_bus.addr,  -- address
      addr_i    => p_bus.addr,  -- address
      rden_i    => io_rden,     -- read enable
      rden_i    => io_rden,     -- read enable
      wren_i    => io_wren,     -- write enable
      wren_i    => io_wren,     -- write enable
      data_i    => p_bus.wdata, -- data in
      data_i    => p_bus.wdata, -- data in
      data_o    => mtime_rdata, -- data out
      data_o => resp_bus(RESP_MTIME).rdata, -- data out
      ack_o     => mtime_ack,   -- transfer acknowledge
      ack_o  => resp_bus(RESP_MTIME).ack,   -- transfer acknowledge
      -- time output for CPU --
      -- time output for CPU --
      time_o    => mtime_time,  -- current system time
      time_o    => mtime_time,  -- current system time
      -- interrupt --
      -- interrupt --
      irq_o     => mtime_irq    -- interrupt request
      irq_o     => mtime_irq    -- interrupt request
    );
    );
 
    resp_bus(RESP_MTIME).err <= '0'; -- no access error possible
  end generate;
  end generate;
 
 
  neorv32_mtime_inst_false:
  neorv32_mtime_inst_false:
  if (IO_MTIME_EN = false) generate
  if (IO_MTIME_EN = false) generate
    mtime_rdata <= (others => '0');
    resp_bus(RESP_MTIME) <= resp_bus_entry_terminate_c;
    mtime_time  <= mtime_i; -- use external machine timer time signal
    mtime_time  <= mtime_i; -- use external machine timer time signal
    mtime_ack   <= '0';
 
    mtime_irq   <= mtime_irq_i; -- use external machine timer interrupt
    mtime_irq   <= mtime_irq_i; -- use external machine timer interrupt
  end generate;
  end generate;
 
 
  mtime_o <= mtime_time when (IO_MTIME_EN = true) else (others => '0'); -- system time output
 
 
  -- system time output LO --
 
  mtime_sync: process(clk_i)
 
  begin
 
    if rising_edge(clk_i) then
 
      -- buffer low word one clock cycle to compensate for MTIME's 1-cycle delay
 
      -- when overflowing from low-word to high-word -> only relevant for processor-external devices
 
      -- processor-internal devices (= the CPU) do not care about this delay offset as 64-bit MTIME.TIME
 
      -- cannot be accessed within a single cycle
 
      if (IO_MTIME_EN = true) then
 
        mtime_o(31 downto 0) <= mtime_time(31 downto 0);
 
      else
 
        mtime_o(31 downto 0) <= (others => '0');
 
      end if;
 
    end if;
 
  end process mtime_sync;
 
 
 
  -- system time output HI --
 
  mtime_o(63 downto 32) <= mtime_time(63 downto 32) when (IO_MTIME_EN = true) else (others => '0');
 
 
 
 
  -- Primary Universal Asynchronous Receiver/Transmitter (UART0) ----------------------------
  -- Primary Universal Asynchronous Receiver/Transmitter (UART0) ----------------------------
  -- -------------------------------------------------------------------------------------------
  -- -------------------------------------------------------------------------------------------
  neorv32_uart0_inst_true:
  neorv32_uart0_inst_true:
Line 996... Line 975...
      clk_i       => clk_i,         -- global clock line
      clk_i       => clk_i,         -- global clock line
      addr_i      => p_bus.addr,    -- address
      addr_i      => p_bus.addr,    -- address
      rden_i      => io_rden,       -- read enable
      rden_i      => io_rden,       -- read enable
      wren_i      => io_wren,       -- write enable
      wren_i      => io_wren,       -- write enable
      data_i      => p_bus.wdata,   -- data in
      data_i      => p_bus.wdata,   -- data in
      data_o      => uart0_rdata,   -- data out
      data_o      => resp_bus(RESP_UART0).rdata, -- data out
      ack_o       => uart0_ack,     -- transfer acknowledge
      ack_o       => resp_bus(RESP_UART0).ack,   -- transfer acknowledge
      -- clock generator --
      -- clock generator --
      clkgen_en_o => uart0_cg_en,   -- enable clock generator
      clkgen_en_o => uart0_cg_en,   -- enable clock generator
      clkgen_i    => clk_gen,
      clkgen_i    => clk_gen,
      -- com lines --
      -- com lines --
      uart_txd_o  => uart0_txd_o,
      uart_txd_o  => uart0_txd_o,
Line 1011... Line 990...
      uart_cts_i  => uart0_cts_i,   -- UART.TX allowed to transmit, low-active, optional
      uart_cts_i  => uart0_cts_i,   -- UART.TX allowed to transmit, low-active, optional
      -- interrupts --
      -- interrupts --
      irq_rxd_o   => uart0_rxd_irq, -- uart data received interrupt
      irq_rxd_o   => uart0_rxd_irq, -- uart data received interrupt
      irq_txd_o   => uart0_txd_irq  -- uart transmission done interrupt
      irq_txd_o   => uart0_txd_irq  -- uart transmission done interrupt
    );
    );
 
    resp_bus(RESP_UART0).err <= '0'; -- no access error possible
  end generate;
  end generate;
 
 
  neorv32_uart0_inst_false:
  neorv32_uart0_inst_false:
  if (IO_UART0_EN = false) generate
  if (IO_UART0_EN = false) generate
    uart0_rdata   <= (others => '0');
    resp_bus(RESP_UART0) <= resp_bus_entry_terminate_c;
    uart0_ack     <= '0';
 
    uart0_txd_o   <= '0';
    uart0_txd_o   <= '0';
    uart0_rts_o   <= '0';
    uart0_rts_o   <= '0';
    uart0_cg_en   <= '0';
    uart0_cg_en   <= '0';
    uart0_rxd_irq <= '0';
    uart0_rxd_irq <= '0';
    uart0_txd_irq <= '0';
    uart0_txd_irq <= '0';
Line 1040... Line 1019...
      clk_i       => clk_i,         -- global clock line
      clk_i       => clk_i,         -- global clock line
      addr_i      => p_bus.addr,    -- address
      addr_i      => p_bus.addr,    -- address
      rden_i      => io_rden,       -- read enable
      rden_i      => io_rden,       -- read enable
      wren_i      => io_wren,       -- write enable
      wren_i      => io_wren,       -- write enable
      data_i      => p_bus.wdata,   -- data in
      data_i      => p_bus.wdata,   -- data in
      data_o      => uart1_rdata,   -- data out
      data_o      => resp_bus(RESP_UART1).rdata, -- data out
      ack_o       => uart1_ack,     -- transfer acknowledge
      ack_o       => resp_bus(RESP_UART1).ack,   -- transfer acknowledge
      -- clock generator --
      -- clock generator --
      clkgen_en_o => uart1_cg_en,   -- enable clock generator
      clkgen_en_o => uart1_cg_en,   -- enable clock generator
      clkgen_i    => clk_gen,
      clkgen_i    => clk_gen,
      -- com lines --
      -- com lines --
      uart_txd_o  => uart1_txd_o,
      uart_txd_o  => uart1_txd_o,
Line 1055... Line 1034...
      uart_cts_i  => uart1_cts_i,   -- UART.TX allowed to transmit, low-active, optional
      uart_cts_i  => uart1_cts_i,   -- UART.TX allowed to transmit, low-active, optional
      -- interrupts --
      -- interrupts --
      irq_rxd_o   => uart1_rxd_irq, -- uart data received interrupt
      irq_rxd_o   => uart1_rxd_irq, -- uart data received interrupt
      irq_txd_o   => uart1_txd_irq  -- uart transmission done interrupt
      irq_txd_o   => uart1_txd_irq  -- uart transmission done interrupt
    );
    );
 
    resp_bus(RESP_UART1).err <= '0'; -- no access error possible
  end generate;
  end generate;
 
 
  neorv32_uart1_inst_false:
  neorv32_uart1_inst_false:
  if (IO_UART1_EN = false) generate
  if (IO_UART1_EN = false) generate
    uart1_rdata   <= (others => '0');
    resp_bus(RESP_UART1) <= resp_bus_entry_terminate_c;
    uart1_ack     <= '0';
 
    uart1_txd_o   <= '0';
    uart1_txd_o   <= '0';
    uart1_rts_o   <= '0';
    uart1_rts_o   <= '0';
    uart1_cg_en   <= '0';
    uart1_cg_en   <= '0';
    uart1_rxd_irq <= '0';
    uart1_rxd_irq <= '0';
    uart1_txd_irq <= '0';
    uart1_txd_irq <= '0';
Line 1081... Line 1060...
      clk_i       => clk_i,       -- global clock line
      clk_i       => clk_i,       -- global clock line
      addr_i      => p_bus.addr,  -- address
      addr_i      => p_bus.addr,  -- address
      rden_i      => io_rden,     -- read enable
      rden_i      => io_rden,     -- read enable
      wren_i      => io_wren,     -- write enable
      wren_i      => io_wren,     -- write enable
      data_i      => p_bus.wdata, -- data in
      data_i      => p_bus.wdata, -- data in
      data_o      => spi_rdata,   -- data out
      data_o      => resp_bus(RESP_SPI).rdata, -- data out
      ack_o       => spi_ack,     -- transfer acknowledge
      ack_o       => resp_bus(RESP_SPI).ack,   -- transfer acknowledge
      -- clock generator --
      -- clock generator --
      clkgen_en_o => spi_cg_en,   -- enable clock generator
      clkgen_en_o => spi_cg_en,   -- enable clock generator
      clkgen_i    => clk_gen,
      clkgen_i    => clk_gen,
      -- com lines --
      -- com lines --
      spi_sck_o   => spi_sck_o,   -- SPI serial clock
      spi_sck_o   => spi_sck_o,   -- SPI serial clock
Line 1094... Line 1073...
      spi_sdi_i   => spi_sdi_i,   -- controller data in, peripheral data out
      spi_sdi_i   => spi_sdi_i,   -- controller data in, peripheral data out
      spi_csn_o   => spi_csn_o,   -- SPI CS
      spi_csn_o   => spi_csn_o,   -- SPI CS
      -- interrupt --
      -- interrupt --
      irq_o       => spi_irq      -- transmission done interrupt
      irq_o       => spi_irq      -- transmission done interrupt
    );
    );
 
    resp_bus(RESP_SPI).err <= '0'; -- no access error possible
  end generate;
  end generate;
 
 
  neorv32_spi_inst_false:
  neorv32_spi_inst_false:
  if (IO_SPI_EN = false) generate
  if (IO_SPI_EN = false) generate
    spi_rdata  <= (others => '0');
    resp_bus(RESP_SPI) <= resp_bus_entry_terminate_c;
    spi_ack    <= '0';
 
    spi_sck_o  <= '0';
    spi_sck_o  <= '0';
    spi_sdo_o  <= '0';
    spi_sdo_o  <= '0';
    spi_csn_o  <= (others => '1'); -- CSn lines are low-active
    spi_csn_o  <= (others => '1'); -- CSn lines are low-active
    spi_cg_en  <= '0';
    spi_cg_en  <= '0';
    spi_irq    <= '0';
    spi_irq    <= '0';
Line 1120... Line 1099...
      clk_i       => clk_i,       -- global clock line
      clk_i       => clk_i,       -- global clock line
      addr_i      => p_bus.addr,  -- address
      addr_i      => p_bus.addr,  -- address
      rden_i      => io_rden,     -- read enable
      rden_i      => io_rden,     -- read enable
      wren_i      => io_wren,     -- write enable
      wren_i      => io_wren,     -- write enable
      data_i      => p_bus.wdata, -- data in
      data_i      => p_bus.wdata, -- data in
      data_o      => twi_rdata,   -- data out
      data_o      => resp_bus(RESP_TWI).rdata, -- data out
      ack_o       => twi_ack,     -- transfer acknowledge
      ack_o       => resp_bus(RESP_TWI).ack,   -- transfer acknowledge
      -- clock generator --
      -- clock generator --
      clkgen_en_o => twi_cg_en,   -- enable clock generator
      clkgen_en_o => twi_cg_en,   -- enable clock generator
      clkgen_i    => clk_gen,
      clkgen_i    => clk_gen,
      -- com lines --
      -- com lines --
      twi_sda_io  => twi_sda_io,  -- serial data line
      twi_sda_io  => twi_sda_io,  -- serial data line
      twi_scl_io  => twi_scl_io,  -- serial clock line
      twi_scl_io  => twi_scl_io,  -- serial clock line
      -- interrupt --
      -- interrupt --
      irq_o       => twi_irq      -- transfer done IRQ
      irq_o       => twi_irq      -- transfer done IRQ
    );
    );
 
    resp_bus(RESP_TWI).err <= '0'; -- no access error possible
  end generate;
  end generate;
 
 
  neorv32_twi_inst_false:
  neorv32_twi_inst_false:
  if (IO_TWI_EN = false) generate
  if (IO_TWI_EN = false) generate
    twi_rdata  <= (others => '0');
    resp_bus(RESP_TWI) <= resp_bus_entry_terminate_c;
    twi_ack    <= '0';
 
--  twi_sda_io <= 'Z'; -- FIXME?
--  twi_sda_io <= 'Z'; -- FIXME?
--  twi_scl_io <= 'Z'; -- FIXME?
--  twi_scl_io <= 'Z'; -- FIXME?
    twi_cg_en  <= '0';
    twi_cg_en  <= '0';
    twi_irq    <= '0';
    twi_irq    <= '0';
  end generate;
  end generate;
 
 
 
 
  -- Pulse-Width Modulation Controller (PWM) ------------------------------------------------
  -- Pulse-Width Modulation Controller (PWM) ------------------------------------------------
  -- -------------------------------------------------------------------------------------------
  -- -------------------------------------------------------------------------------------------
  neorv32_pwm_inst_true:
  neorv32_pwm_inst_true:
  if (IO_PWM_EN = true) generate
  if (IO_PWM_NUM_CH > 0) generate
    neorv32_pwm_inst: neorv32_pwm
    neorv32_pwm_inst: neorv32_pwm
 
    generic map (
 
      NUM_CHANNELS => IO_PWM_NUM_CH -- number of PWM channels (0..60)
 
    )
    port map (
    port map (
      -- host access --
      -- host access --
      clk_i       => clk_i,       -- global clock line
      clk_i       => clk_i,       -- global clock line
      addr_i      => p_bus.addr,  -- address
      addr_i      => p_bus.addr,  -- address
      rden_i      => io_rden,     -- read enable
      rden_i      => io_rden,     -- read enable
      wren_i      => io_wren,     -- write enable
      wren_i      => io_wren,     -- write enable
      data_i      => p_bus.wdata, -- data in
      data_i      => p_bus.wdata, -- data in
      data_o      => pwm_rdata,   -- data out
      data_o      => resp_bus(RESP_PWM).rdata, -- data out
      ack_o       => pwm_ack,     -- transfer acknowledge
      ack_o       => resp_bus(RESP_PWM).ack,   -- transfer acknowledge
      -- clock generator --
      -- clock generator --
      clkgen_en_o => pwm_cg_en,   -- enable clock generator
      clkgen_en_o => pwm_cg_en,   -- enable clock generator
      clkgen_i    => clk_gen,
      clkgen_i    => clk_gen,
      -- pwm output channels --
      -- pwm output channels --
      pwm_o       => pwm_o
      pwm_o       => pwm_o
    );
    );
 
    resp_bus(RESP_PWM).err <= '0'; -- no access error possible
  end generate;
  end generate;
 
 
  neorv32_pwm_inst_false:
  neorv32_pwm_inst_false:
  if (IO_PWM_EN = false) generate
  if (IO_PWM_NUM_CH = 0) generate
    pwm_rdata <= (others => '0');
    resp_bus(RESP_PWM) <= resp_bus_entry_terminate_c;
    pwm_ack   <= '0';
 
    pwm_cg_en <= '0';
    pwm_cg_en <= '0';
    pwm_o     <= (others => '0');
    pwm_o     <= (others => '0');
  end generate;
  end generate;
 
 
 
 
Line 1187... Line 1169...
      clk_i       => clk_i,       -- global clock line
      clk_i       => clk_i,       -- global clock line
      addr_i      => p_bus.addr,  -- address
      addr_i      => p_bus.addr,  -- address
      rden_i      => io_rden,     -- read enable
      rden_i      => io_rden,     -- read enable
      wren_i      => io_wren,     -- write enable
      wren_i      => io_wren,     -- write enable
      data_i      => p_bus.wdata, -- data in
      data_i      => p_bus.wdata, -- data in
      data_o      => nco_rdata,   -- data out
      data_o      => resp_bus(RESP_NCO).rdata, -- data out
      ack_o       => nco_ack,     -- transfer acknowledge
      ack_o       => resp_bus(RESP_NCO).ack,   -- transfer acknowledge
      -- clock generator --
      -- clock generator --
      clkgen_en_o => nco_cg_en,   -- enable clock generator
      clkgen_en_o => nco_cg_en,   -- enable clock generator
      clkgen_i    => clk_gen,
      clkgen_i    => clk_gen,
      -- NCO output --
      -- NCO output --
      nco_o       => nco_o
      nco_o       => nco_o
    );
    );
 
    resp_bus(RESP_NCO).err <= '0'; -- no access error possible
  end generate;
  end generate;
 
 
  neorv32_nco_inst_false:
  neorv32_nco_inst_false:
  if (IO_NCO_EN = false) generate
  if (IO_NCO_EN = false) generate
    nco_rdata <= (others => '0');
    resp_bus(RESP_NCO) <= resp_bus_entry_terminate_c;
    nco_ack   <= '0';
 
    nco_cg_en <= '0';
    nco_cg_en <= '0';
    nco_o     <= (others => '0');
    nco_o     <= (others => '0');
  end generate;
  end generate;
 
 
 
 
Line 1218... Line 1200...
      clk_i  => clk_i,       -- global clock line
      clk_i  => clk_i,       -- global clock line
      addr_i => p_bus.addr,  -- address
      addr_i => p_bus.addr,  -- address
      rden_i => io_rden,     -- read enable
      rden_i => io_rden,     -- read enable
      wren_i => io_wren,     -- write enable
      wren_i => io_wren,     -- write enable
      data_i => p_bus.wdata, -- data in
      data_i => p_bus.wdata, -- data in
      data_o => trng_rdata,  -- data out
      data_o => resp_bus(RESP_TRNG).rdata, -- data out
      ack_o  => trng_ack     -- transfer acknowledge
      ack_o  => resp_bus(RESP_TRNG).ack    -- transfer acknowledge
    );
    );
 
    resp_bus(RESP_TRNG).err <= '0'; -- no access error possible
  end generate;
  end generate;
 
 
  neorv32_trng_inst_false:
  neorv32_trng_inst_false:
  if (IO_TRNG_EN = false) generate
  if (IO_TRNG_EN = false) generate
    trng_rdata <= (others => '0');
    resp_bus(RESP_TRNG) <= resp_bus_entry_terminate_c;
    trng_ack   <= '0';
 
  end generate;
  end generate;
 
 
 
 
  -- Smart LED (WS2811/WS2812) Interface (NEOLED) -------------------------------------------
  -- Smart LED (WS2811/WS2812) Interface (NEOLED) -------------------------------------------
  -- -------------------------------------------------------------------------------------------
  -- -------------------------------------------------------------------------------------------
Line 1242... Line 1224...
      clk_i       => clk_i,        -- global clock line
      clk_i       => clk_i,        -- global clock line
      addr_i      => p_bus.addr,   -- address
      addr_i      => p_bus.addr,   -- address
      rden_i      => io_rden,      -- read enable
      rden_i      => io_rden,      -- read enable
      wren_i      => io_wren,      -- write enable
      wren_i      => io_wren,      -- write enable
      data_i      => p_bus.wdata,  -- data in
      data_i      => p_bus.wdata,  -- data in
      data_o      => neoled_rdata, -- data out
      data_o      => resp_bus(RESP_NEOLED).rdata, -- data out
      ack_o       => neoled_ack,   -- transfer acknowledge
      ack_o       => resp_bus(RESP_NEOLED).ack,   -- transfer acknowledge
      -- clock generator --
      -- clock generator --
      clkgen_en_o => neoled_cg_en, -- enable clock generator
      clkgen_en_o => neoled_cg_en, -- enable clock generator
      clkgen_i    => clk_gen,
      clkgen_i    => clk_gen,
      -- interrupt --
      -- interrupt --
      irq_o       => neoled_irq,   -- interrupt request
      irq_o       => neoled_irq,   -- interrupt request
      -- NEOLED output --
      -- NEOLED output --
      neoled_o    => neoled_o      -- serial async data line
      neoled_o    => neoled_o      -- serial async data line
    );
    );
 
    resp_bus(RESP_NEOLED).err <= '0'; -- no access error possible
  end generate;
  end generate;
 
 
  neorv32_neoled_inst_false:
  neorv32_neoled_inst_false:
  if (IO_NEOLED_EN = false) generate
  if (IO_NEOLED_EN = false) generate
    neoled_rdata <= (others => '0');
    resp_bus(RESP_NEOLED) <= resp_bus_entry_terminate_c;
    neoled_ack   <= '0';
 
    neoled_cg_en <= '0';
    neoled_cg_en <= '0';
    neoled_irq   <= '0';
    neoled_irq   <= '0';
    neoled_o     <= '0';
    neoled_o     <= '0';
  end generate;
  end generate;
 
 
Line 1295... Line 1277...
    IO_MTIME_EN          => IO_MTIME_EN,          -- implement machine system timer (MTIME)?
    IO_MTIME_EN          => IO_MTIME_EN,          -- implement machine system timer (MTIME)?
    IO_UART0_EN          => IO_UART0_EN,          -- implement primary universal asynchronous receiver/transmitter (UART0)?
    IO_UART0_EN          => IO_UART0_EN,          -- implement primary universal asynchronous receiver/transmitter (UART0)?
    IO_UART1_EN          => IO_UART1_EN,          -- implement secondary universal asynchronous receiver/transmitter (UART1)?
    IO_UART1_EN          => IO_UART1_EN,          -- implement secondary universal asynchronous receiver/transmitter (UART1)?
    IO_SPI_EN            => IO_SPI_EN,            -- implement serial peripheral interface (SPI)?
    IO_SPI_EN            => IO_SPI_EN,            -- implement serial peripheral interface (SPI)?
    IO_TWI_EN            => IO_TWI_EN,            -- implement two-wire interface (TWI)?
    IO_TWI_EN            => IO_TWI_EN,            -- implement two-wire interface (TWI)?
    IO_PWM_EN            => IO_PWM_EN,            -- implement pulse-width modulation unit (PWM)?
    IO_PWM_NUM_CH        => IO_PWM_NUM_CH,        -- number of PWM channels to implement
    IO_WDT_EN            => IO_WDT_EN,            -- implement watch dog timer (WDT)?
    IO_WDT_EN            => IO_WDT_EN,            -- implement watch dog timer (WDT)?
    IO_TRNG_EN           => IO_TRNG_EN,           -- implement true random number generator (TRNG)?
    IO_TRNG_EN           => IO_TRNG_EN,           -- implement true random number generator (TRNG)?
    IO_CFS_EN            => IO_CFS_EN,            -- implement custom functions subsystem (CFS)?
    IO_CFS_EN            => IO_CFS_EN,            -- implement custom functions subsystem (CFS)?
    IO_NCO_EN            => IO_NCO_EN,            -- implement numerically-controlled oscillator (NCO)?
    IO_NCO_EN            => IO_NCO_EN,            -- implement numerically-controlled oscillator (NCO)?
    IO_NEOLED_EN         => IO_NEOLED_EN          -- implement NeoPixel-compatible smart LED interface (NEOLED)?
    IO_NEOLED_EN         => IO_NEOLED_EN          -- implement NeoPixel-compatible smart LED interface (NEOLED)?
Line 1307... Line 1289...
  port map (
  port map (
    -- host access --
    -- host access --
    clk_i  => clk_i,         -- global clock line
    clk_i  => clk_i,         -- global clock line
    addr_i => p_bus.addr,    -- address
    addr_i => p_bus.addr,    -- address
    rden_i => io_rden,       -- read enable
    rden_i => io_rden,       -- read enable
    data_o => sysinfo_rdata, -- data out
    data_o => resp_bus(RESP_SYSINFO).rdata, -- data out
    ack_o  => sysinfo_ack    -- transfer acknowledge
    ack_o  => resp_bus(RESP_SYSINFO).ack    -- transfer acknowledge
  );
  );
 
 
 
  resp_bus(RESP_SYSINFO).err <= '0'; -- no access error possible
 
 
 
 
  -- **************************************************************************************************************************
  -- **************************************************************************************************************************
  -- On-Chip Debugger Complex
  -- On-Chip Debugger Complex
  -- **************************************************************************************************************************
  -- **************************************************************************************************************************
 
 
Line 1342... Line 1326...
      -- CPU bus access --
      -- CPU bus access --
      cpu_addr_i       => p_bus.addr,     -- address
      cpu_addr_i       => p_bus.addr,     -- address
      cpu_rden_i       => p_bus.re,       -- read enable
      cpu_rden_i       => p_bus.re,       -- read enable
      cpu_wren_i       => p_bus.we,       -- write enable
      cpu_wren_i       => p_bus.we,       -- write enable
      cpu_data_i       => p_bus.wdata,    -- data in
      cpu_data_i       => p_bus.wdata,    -- data in
      cpu_data_o       => dm_rdata,       -- data out
      cpu_data_o       => resp_bus(RESP_OCD).rdata, -- data out
      cpu_ack_o        => dm_ack,         -- transfer acknowledge
      cpu_ack_o        => resp_bus(RESP_OCD).ack,   -- transfer acknowledge
      -- CPU control --
      -- CPU control --
      cpu_ndmrstn_o    => dci_ndmrstn,    -- soc reset
      cpu_ndmrstn_o    => dci_ndmrstn,    -- soc reset
      cpu_halt_req_o   => dci_halt_req    -- request hart to halt (enter debug mode)
      cpu_halt_req_o   => dci_halt_req    -- request hart to halt (enter debug mode)
    );
    );
 
    resp_bus(RESP_OCD).err <= '0'; -- no access error possible
  end generate;
  end generate;
 
 
  neorv32_debug_dm_false:
  neorv32_debug_dm_false:
  if (ON_CHIP_DEBUGGER_EN = false) generate
  if (ON_CHIP_DEBUGGER_EN = false) generate
    dmi.req_ready  <= '0';
    dmi.req_ready  <= '0';
    dmi.resp_valid <= '0';
    dmi.resp_valid <= '0';
    dmi.resp_data  <= (others => '0');
    dmi.resp_data  <= (others => '0');
    dmi.resp_err   <= '0';
    dmi.resp_err   <= '0';
    --
    --
    dci_ndmrstn    <= '0';
    resp_bus(RESP_OCD) <= resp_bus_entry_terminate_c;
 
    dci_ndmrstn  <= '1';
    dci_halt_req   <= '0';
    dci_halt_req   <= '0';
    dm_rdata       <= (others => '0');
 
    dm_ack         <= '0';
 
  end generate;
  end generate;
 
 
 
 
  -- On-Chip Debugger - Debug Transport Module (DTM) ----------------------------------------
  -- On-Chip Debugger - Debug Transport Module (DTM) ----------------------------------------
  -- -------------------------------------------------------------------------------------------
  -- -------------------------------------------------------------------------------------------

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.