-- -- Top-level FPGA design for Red Pitaya PuzzleFW firmware. -- -- Joris van Rantwijk 2024 -- library ieee; use ieee.std_logic_1164.all; use ieee.std_logic_misc.all; use ieee.numeric_std.all; library unisim; use unisim.vcomponents.all; library xpm; use xpm.vcomponents.all; use work.puzzlefw_pkg.all; entity puzzlefw_top is port ( -- Ports directly connected to ARM/PS. DDR_0_addr: inout std_logic_vector(14 downto 0); DDR_0_ba: inout std_logic_vector(2 downto 0); DDR_0_cas_n: inout std_logic; DDR_0_ck_n: inout std_logic; DDR_0_ck_p: inout std_logic; DDR_0_cke: inout std_logic; DDR_0_cs_n: inout std_logic; DDR_0_dm: inout std_logic_vector(3 downto 0); DDR_0_dq: inout std_logic_vector(31 downto 0); DDR_0_dqs_n: inout std_logic_vector(3 downto 0); DDR_0_dqs_p: inout std_logic_vector(3 downto 0); DDR_0_odt: inout std_logic; DDR_0_ras_n: inout std_logic; DDR_0_reset_n: inout std_logic; DDR_0_we_n: inout std_logic; FIXED_IO_0_ddr_vrn: inout std_logic; FIXED_IO_0_ddr_vrp: inout std_logic; FIXED_IO_0_mio: inout std_logic_vector(53 downto 0); FIXED_IO_0_ps_clk: inout std_logic; FIXED_IO_0_ps_porb: inout std_logic; FIXED_IO_0_ps_srstb: inout std_logic; -- Ports controlled by FPGA. adc_dat_i: in adc_data_input_type; -- ADC data adc_clk_i: in std_logic_vector(1 downto 0); -- ADC clock 1=pos, 0=neg adc_clk_o: out std_logic_vector(1 downto 0); -- optional clock output for ADC adc_cdcs_o: out std_logic; -- ADC clock duty cycle stabilizer dac_dat_o: out std_logic_vector(13 downto 0); -- DAC data dac_wrt_o: out std_logic; -- DAC write control dac_sel_o: out std_logic; -- DAC channel select dac_clk_o: out std_logic; -- DAC clock dac_rst_o: out std_logic; -- DAC reset dac_pwm_o: out std_logic_vector(3 downto 0); -- PWM DAC exp_p_io: inout std_logic_vector(7 downto 0); -- extension I/O pos exp_n_io: inout std_logic_vector(7 downto 0); -- extension I/O neg led_o: out std_logic_vector(7 downto 0) -- LEDs ); end puzzlefw_top; architecture arch of puzzlefw_top is -- Main 125 MHz clock, derived from ADC clock input port. signal clk_adc: std_logic; -- Auxiliary clock from FCLK0. signal clk_fclk: std_logic; -- Reset signals. signal s_ext_reset_n: std_logic; -- reset signal from GPIO, active low signal s_pll_reset: std_logic; -- reset signal for PLL signal s_pll_locked: std_logic; -- PLL locked status signal s_reset: std_logic; -- main reset, synchronized to clk_adc signal r_reset_done: std_logic; -- reset status report via GPIO -- Internal clock signals. signal s_adc_clk_ibuf: std_logic; signal s_pll_clkfbout: std_logic; signal s_pll_clkfbin: std_logic; signal s_pll_clkout: std_logic; -- Blinking LED. signal r_adcclk_cnt: unsigned(25 downto 0); signal r_adcclk_led: std_logic; -- Internal GPIO bus from PS. signal s_gpio_in: std_logic_vector(23 downto 0); signal s_gpio_out: std_logic_vector(23 downto 0); -- APB bus for register access. signal s_apb_paddr: std_logic_vector(31 downto 0); signal s_apb_penable: std_logic; signal s_apb_prdata: std_logic_vector(31 downto 0); signal s_apb_pready: std_logic; signal s_apb_psel: std_logic; signal s_apb_pslverr: std_logic; signal s_apb_pwdata: std_logic_vector(31 downto 0); signal s_apb_pwrite: std_logic; -- AXI bus for DMA. signal s_axi_awid: std_logic_vector(5 downto 0); signal s_axi_awaddr: std_logic_vector(31 downto 0); signal s_axi_awlen: std_logic_vector(3 downto 0); signal s_axi_awsize: std_logic_vector(2 downto 0); signal s_axi_awburst: std_logic_vector(1 downto 0); signal s_axi_awlock: std_logic_vector(1 downto 0); signal s_axi_awcache: std_logic_vector(3 downto 0); signal s_axi_awprot: std_logic_vector(2 downto 0); signal s_axi_awqos: std_logic_vector(3 downto 0); signal s_axi_awvalid: std_logic; signal s_axi_awready: std_logic; signal s_axi_wid: std_logic_vector(5 downto 0); signal s_axi_wdata: std_logic_vector(63 downto 0); signal s_axi_wstrb: std_logic_vector(7 downto 0); signal s_axi_wlast: std_logic; signal s_axi_wvalid: std_logic; signal s_axi_wready: std_logic; signal s_axi_bid: std_logic_vector(5 downto 0); signal s_axi_bresp: std_logic_vector(1 downto 0); signal s_axi_bvalid: std_logic; signal s_axi_bready: std_logic; signal s_axi_arid: std_logic_vector(5 downto 0); signal s_axi_araddr: std_logic_vector(31 downto 0); signal s_axi_arlen: std_logic_vector(3 downto 0); signal s_axi_arsize: std_logic_vector(2 downto 0); signal s_axi_arburst: std_logic_vector(1 downto 0); signal s_axi_arlock: std_logic_vector(1 downto 0); signal s_axi_arcache: std_logic_vector(3 downto 0); signal s_axi_arprot: std_logic_vector(2 downto 0); signal s_axi_arqos: std_logic_vector(3 downto 0); signal s_axi_arvalid: std_logic; signal s_axi_arready: std_logic; signal s_axi_rid: std_logic_vector(5 downto 0); signal s_axi_rdata: std_logic_vector(63 downto 0); signal s_axi_rresp: std_logic_vector(1 downto 0); signal s_axi_rlast: std_logic; signal s_axi_rvalid: std_logic; signal s_axi_rready: std_logic; -- Interrupts. signal s_irq_pending: std_logic_vector(1 downto 0); signal s_irq_f2p: std_logic_vector(7 downto 0); -- Registers. signal s_reg_control: registers_control; signal s_reg_status: registers_status; -- DMA write channel control. signal s_dma_write_cmd_addr: dma_address_array(0 to 1); signal s_dma_write_cmd_length: dma_burst_length_array(0 to 1); signal s_dma_write_cmd_valid: std_logic_vector(1 downto 0); signal s_dma_write_cmd_ready: std_logic_vector(1 downto 0); signal s_dma_write_data: dma_data_array(0 to 1); signal s_dma_write_data_ready: std_logic_vector(1 downto 0); signal s_dma_write_finished: std_logic_vector(1 downto 0); signal s_acq_dma_valid: std_logic; signal s_acq_dma_ready: std_logic; signal s_acq_dma_empty: std_logic; signal s_acq_dma_data: dma_data_type; signal s_tt_dma_valid: std_logic; signal s_tt_dma_ready: std_logic; signal s_tt_dma_empty: std_logic; signal s_tt_dma_data: dma_data_type; signal s_timestamp: std_logic_vector(timestamp_bits - 1 downto 0); signal s_adc_data: adc_data_array(0 to 1); signal s_adc_sample: adc_data_array(0 to 1); signal s_dig_in: std_logic_vector(3 downto 0); signal s_dig_sync: std_logic_vector(3 downto 0); signal s_dig_deglitch: std_logic_vector(3 downto 0); signal s_dig_sample: std_logic_vector(3 downto 0); begin -- Global FPGA reset. -- GPIO(0) = '0' to reset. s_ext_reset_n <= s_gpio_out(0); -- ADC clock duty cycle stabilizer. -- GPIO(2) = '1' to enable, '0' to disable. adc_cdcs_o <= s_gpio_out(2); -- GPIO inputs to the PS. -- GPIO(1) = '0' while in reset, '1' when reset released. s_gpio_in(1) <= r_reset_done; s_gpio_in(0) <= '0'; s_gpio_in(23 downto 2) <= (others => '0'); -- Drive LEDs. led_o(0) <= r_adcclk_led; -- blinking LED, 1 Hz led_o(1) <= s_reg_control.acquisition_en; -- acquisition enabled led_o(2) <= s_reg_status.trig_waiting; -- waiting for trigger led_o(3) <= or_reduce(s_reg_control.timetagger_en); -- timetagger enabled led_o(7 downto 4) <= s_reg_control.led_state(7 downto 4); -- ADC clock outputs are not connected on vanilla Red Pitaya 125-14. adc_clk_o <= (others => 'Z'); -- Drive safe levels to unused DAC pins. dac_dat_o <= (others => '0'); dac_wrt_o <= '0'; dac_sel_o <= '0'; dac_clk_o <= '0'; dac_rst_o <= '0'; dac_pwm_o <= (others => 'Z'); -- Use extension I/O pins as inputs only. exp_p_io <= (others => 'Z'); exp_n_io <= (others => 'Z'); -- Differential clock input for ADC clock. inst_ibuf_adc_clk: IBUFDS port map ( O => s_adc_clk_ibuf, I => adc_clk_i(1), IB => adc_clk_i(0) ); -- PLL for 125 MHz clock. -- Input clock comes from ADC. -- Output clock drives most of the FPGA design. -- Output clock shifted to optimize capturing of ADC samples. inst_pll: PLLE2_BASE generic map ( BANDWIDTH => "OPTIMIZED", CLKFBOUT_MULT => 7, CLKFBOUT_PHASE => 0.0, CLKIN1_PERIOD => 8.0, CLKOUT0_DIVIDE => 7, CLKOUT0_DUTY_CYCLE => 0.5, CLKOUT0_PHASE => 90.0, DIVCLK_DIVIDE => 1, STARTUP_WAIT => "FALSE" ) port map ( CLKOUT0 => s_pll_clkout, CLKFBOUT => s_pll_clkfbout, LOCKED => s_pll_locked, CLKIN1 => s_adc_clk_ibuf, PWRDWN => '0', RST => s_pll_reset, CLKFBIN => s_pll_clkfbin ); -- Reset PLL when external reset is applied. s_pll_reset <= not s_ext_reset_n; -- Clock buffers for PLL. inst_bufg_pll_clkfb: BUFG port map ( I => s_pll_clkfbout, O => s_pll_clkfbin ); inst_bufg_pll_clkout: BUFG port map ( I => s_pll_clkout, O => clk_adc ); -- ARM/PS block design. inst_blockdesign: entity work.puzzlefw_wrapper port map ( sys_clk => clk_adc, ps_fclk => clk_fclk, peripheral_reset_0(0) => s_reset, ext_reset_in_0 => s_ext_reset_n, dcm_locked_0 => s_pll_locked, DDR_0_addr => DDR_0_addr, DDR_0_ba => DDR_0_ba, DDR_0_cas_n => DDR_0_cas_n, DDR_0_ck_n => DDR_0_ck_n, DDR_0_ck_p => DDR_0_ck_p, DDR_0_cke => DDR_0_cke, DDR_0_cs_n => DDR_0_cs_n, DDR_0_dm => DDR_0_dm, DDR_0_dq => DDR_0_dq, DDR_0_dqs_n => DDR_0_dqs_n, DDR_0_dqs_p => DDR_0_dqs_p, DDR_0_odt => DDR_0_odt, DDR_0_ras_n => DDR_0_ras_n, DDR_0_reset_n => DDR_0_reset_n, DDR_0_we_n => DDR_0_we_n, FIXED_IO_0_ddr_vrn => FIXED_IO_0_ddr_vrn, FIXED_IO_0_ddr_vrp => FIXED_IO_0_ddr_vrp, FIXED_IO_0_mio => FIXED_IO_0_mio, FIXED_IO_0_ps_clk => FIXED_IO_0_ps_clk, FIXED_IO_0_ps_porb => FIXED_IO_0_ps_porb, FIXED_IO_0_ps_srstb => FIXED_IO_0_ps_srstb, GPIO_I_0 => s_gpio_in, GPIO_O_0 => s_gpio_out, SPI0_MOSI_O_0 => open, SPI0_MOSI_T_0 => open, SPI0_SCLK_O_0 => open, SPI0_SCLK_T_0 => open, SPI0_SS1_O_0 => open, SPI0_SS_O_0 => open, SPI0_SS_T_0 => open, IRQ_F2P => s_irq_f2p, APB_M_0_paddr => s_apb_paddr, APB_M_0_penable => s_apb_penable, APB_M_0_prdata => s_apb_prdata, APB_M_0_pready(0) => s_apb_pready, APB_M_0_psel(0) => s_apb_psel, APB_M_0_pslverr(0) => s_apb_pslverr, APB_M_0_pwdata => s_apb_pwdata, APB_M_0_pwrite => s_apb_pwrite, S_AXI_HP0_0_araddr => s_axi_araddr, S_AXI_HP0_0_arburst => s_axi_arburst, S_AXI_HP0_0_arcache => s_axi_arcache, S_AXI_HP0_0_arid => s_axi_arid, S_AXI_HP0_0_arlen => s_axi_arlen, S_AXI_HP0_0_arlock => s_axi_arlock, S_AXI_HP0_0_arprot => s_axi_arprot, S_AXI_HP0_0_arqos => s_axi_arqos, S_AXI_HP0_0_arready => s_axi_arready, S_AXI_HP0_0_arsize => s_axi_arsize, S_AXI_HP0_0_arvalid => s_axi_arvalid, S_AXI_HP0_0_awaddr => s_axi_awaddr, S_AXI_HP0_0_awburst => s_axi_awburst, S_AXI_HP0_0_awcache => s_axi_awcache, S_AXI_HP0_0_awid => s_axi_awid, S_AXI_HP0_0_awlen => s_axi_awlen, S_AXI_HP0_0_awlock => s_axi_awlock, S_AXI_HP0_0_awprot => s_axi_awprot, S_AXI_HP0_0_awqos => s_axi_awqos, S_AXI_HP0_0_awready => s_axi_awready, S_AXI_HP0_0_awsize => s_axi_awsize, S_AXI_HP0_0_awvalid => s_axi_awvalid, S_AXI_HP0_0_bid => s_axi_bid, S_AXI_HP0_0_bready => s_axi_bready, S_AXI_HP0_0_bresp => s_axi_bresp, S_AXI_HP0_0_bvalid => s_axi_bvalid, S_AXI_HP0_0_rdata => s_axi_rdata, S_AXI_HP0_0_rid => s_axi_rid, S_AXI_HP0_0_rlast => s_axi_rlast, S_AXI_HP0_0_rready => s_axi_rready, S_AXI_HP0_0_rresp => s_axi_rresp, S_AXI_HP0_0_rvalid => s_axi_rvalid, S_AXI_HP0_0_wdata => s_axi_wdata, S_AXI_HP0_0_wid => s_axi_wid, S_AXI_HP0_0_wlast => s_axi_wlast, S_AXI_HP0_0_wready => s_axi_wready, S_AXI_HP0_0_wstrb => s_axi_wstrb, S_AXI_HP0_0_wvalid => s_axi_wvalid ); -- Memory-mapped registers. inst_registers: entity work.registers generic map ( num_acq_channels => 2 ) port map ( clk => clk_adc, reset => s_reset, apb_psel => s_apb_psel, apb_penable => s_apb_penable, apb_pwrite => s_apb_pwrite, apb_paddr => s_apb_paddr, apb_pwdata => s_apb_pwdata, apb_pready => s_apb_pready, apb_pslverr => s_apb_pslverr, apb_prdata => s_apb_prdata, reg_control => s_reg_control, reg_status => s_reg_status ); -- AXI master. inst_axi_master: entity work.dma_axi_master generic map ( num_read_channels => 0, num_write_channels => 2 ) port map ( clk => clk_adc, reset => s_reset, dma_en => s_reg_control.dma_en, dma_busy => s_reg_status.dma_busy, window_base_addr => s_reg_control.dma_buf_addr, window_size => s_reg_control.dma_buf_size, err_read => s_reg_status.dma_err_read, err_write => s_reg_status.dma_err_write, err_address => s_reg_status.dma_err_address, err_any => s_reg_status.dma_err_any, clear_errors => s_reg_control.dma_clear, read_cmd_addr => (others => (others => '0')), read_cmd_length => (others => (others => '0')), read_cmd_valid => (others => '0'), read_cmd_ready => open, read_data => open, read_data_valid => open, write_cmd_addr => s_dma_write_cmd_addr, write_cmd_length => s_dma_write_cmd_length, write_cmd_valid => s_dma_write_cmd_valid, write_cmd_ready => s_dma_write_cmd_ready, write_data => s_dma_write_data, write_data_ready => s_dma_write_data_ready, write_finished => s_dma_write_finished, m_axi_awid => s_axi_awid, m_axi_awaddr => s_axi_awaddr, m_axi_awlen => s_axi_awlen, m_axi_awsize => s_axi_awsize, m_axi_awburst => s_axi_awburst, m_axi_awlock => s_axi_awlock, m_axi_awcache => s_axi_awcache, m_axi_awprot => s_axi_awprot, m_axi_awqos => s_axi_awqos, m_axi_awvalid => s_axi_awvalid, m_axi_awready => s_axi_awready, m_axi_wid => s_axi_wid, m_axi_wdata => s_axi_wdata, m_axi_wstrb => s_axi_wstrb, m_axi_wlast => s_axi_wlast, m_axi_wvalid => s_axi_wvalid, m_axi_wready => s_axi_wready, m_axi_bid => s_axi_bid, m_axi_bresp => s_axi_bresp, m_axi_bvalid => s_axi_bvalid, m_axi_bready => s_axi_bready, m_axi_arid => s_axi_arid, m_axi_araddr => s_axi_araddr, m_axi_arlen => s_axi_arlen, m_axi_arsize => s_axi_arsize, m_axi_arburst => s_axi_arburst, m_axi_arlock => s_axi_arlock, m_axi_arcache => s_axi_arcache, m_axi_arprot => s_axi_arprot, m_axi_arqos => s_axi_arqos, m_axi_arvalid => s_axi_arvalid, m_axi_arready => s_axi_arready, m_axi_rid => s_axi_rid, m_axi_rdata => s_axi_rdata, m_axi_rresp => s_axi_rresp, m_axi_rlast => s_axi_rlast, m_axi_rvalid => s_axi_rvalid, m_axi_rready => s_axi_rready ); -- DMA write channel for analog acquisition inst_acq_dma: entity work.dma_write_channel generic map ( transfer_size_bits => 4, queue_size_bits => 14, idle_timeout => 256 ) port map ( clk => clk_adc, reset => s_reset, channel_en => s_reg_control.acq_dma_en, channel_busy => s_reg_status.acq_dma_busy, channel_init => s_reg_control.acq_dma_init, addr_start => s_reg_control.acq_addr_start, addr_end => s_reg_control.acq_addr_end, addr_limit => s_reg_control.acq_addr_limit, addr_interrupt => s_reg_control.acq_addr_intr, addr_pointer => s_reg_status.acq_addr_ptr, intr_en => s_reg_control.acq_intr_en, intr_clear => s_reg_control.acq_intr_clear, intr_out => s_irq_pending(0), in_valid => s_acq_dma_valid, in_ready => s_acq_dma_ready, in_empty => s_acq_dma_empty, in_data => s_acq_dma_data, write_cmd_addr => s_dma_write_cmd_addr(0), write_cmd_length => s_dma_write_cmd_length(0), write_cmd_valid => s_dma_write_cmd_valid(0), write_cmd_ready => s_dma_write_cmd_ready(0), write_data => s_dma_write_data(0), write_data_ready => s_dma_write_data_ready(0), write_finished => s_dma_write_finished(0) ); -- DMA write channel for time tagger inst_tt_dma: entity work.dma_write_channel generic map ( transfer_size_bits => 4, queue_size_bits => 12, idle_timeout => 256 ) port map ( clk => clk_adc, reset => s_reset, channel_en => s_reg_control.tt_dma_en, channel_busy => s_reg_status.tt_dma_busy, channel_init => s_reg_control.tt_dma_init, addr_start => s_reg_control.tt_addr_start, addr_end => s_reg_control.tt_addr_end, addr_limit => s_reg_control.tt_addr_limit, addr_interrupt => s_reg_control.tt_addr_intr, addr_pointer => s_reg_status.tt_addr_ptr, intr_en => s_reg_control.tt_intr_en, intr_clear => s_reg_control.tt_intr_clear, intr_out => s_irq_pending(1), in_valid => s_tt_dma_valid, in_ready => s_tt_dma_ready, in_empty => s_tt_dma_empty, in_data => s_tt_dma_data, write_cmd_addr => s_dma_write_cmd_addr(1), write_cmd_length => s_dma_write_cmd_length(1), write_cmd_valid => s_dma_write_cmd_valid(1), write_cmd_ready => s_dma_write_cmd_ready(1), write_data => s_dma_write_data(1), write_data_ready => s_dma_write_data_ready(1), write_finished => s_dma_write_finished(1) ); -- Timestamp generator. inst_timestamp_gen: entity work.timestamp_gen port map ( clk => clk_adc, reset => s_reset, clear => s_reg_control.timestamp_clear, timestamp => s_timestamp ); s_reg_status.timestamp <= s_timestamp; -- Capture ADC data. -- Ignore the 2 LSB bits which are not-connected on the ADC side. inst_capture_gen: for i in 0 to 1 generate inst_adc_capture: entity work.adc_capture port map ( clk => clk_adc, in_data => adc_dat_i(i)(15 downto 2), out_data => s_adc_data(i) ); end generate; -- Optionally generate simulated ADC samples. inst_adc_sample_stream: entity work.adc_sample_stream port map ( clk => clk_adc, reset => s_reset, simulate => s_reg_control.simulate_adc, in_data => s_adc_data(0 to 1), out_data => s_adc_sample(0 to 1) ); -- Monitor range of ADC samples. inst_monitor_gen: for i in 0 to 1 generate inst_range_monitor: entity work.adc_range_monitor generic map ( signed_data => false ) port map ( clk => clk_adc, reset => s_reset, clear => s_reg_control.adc_range_clear, in_data => s_adc_sample(i), min_value => s_reg_status.adc_min_value(i), max_value => s_reg_status.adc_max_value(i) ); end generate; -- Monitor current ADC sample value. s_reg_status.adc_sample(0 to 1) <= s_adc_sample(0 to 1); -- Drive dummy values to not-implemented channels 2, 3. s_reg_status.adc_sample(2 to 3) <= (others => (others => '0')); s_reg_status.adc_min_value(2 to 3) <= (others => (others => '0')); s_reg_status.adc_max_value(2 to 3) <= (others => (others => '0')); -- Analog acquisition data chain. inst_acquisition_chain: entity work.acquisition_chain generic map ( num_channels => 2 ) port map ( clk => clk_adc, reset => s_reset, acquisition_en => s_reg_control.acquisition_en, trigger_delay => s_reg_control.trigger_delay, record_length => s_reg_control.record_length, decimation_factor => s_reg_control.decimation_factor, averaging => s_reg_control.averaging_en, shift_steps => s_reg_control.shift_steps, ch4_mode => s_reg_control.ch4_mode, trig_auto_en => s_reg_control.trig_auto_en, trig_ext_en => s_reg_control.trig_ext_en, trig_ext_once => s_reg_control.trig_ext_once, trig_force => s_reg_control.trig_force, trig_ext_select => s_reg_control.trig_ext_select, trig_ext_falling => s_reg_control.trig_ext_falling, timestamp_in => s_timestamp, adc_data_in => s_adc_sample, trig_ext_in => s_dig_sample, trig_waiting => s_reg_status.trig_waiting, trig_detected => s_reg_status.trig_detected, out_valid => s_acq_dma_valid, out_ready => s_acq_dma_ready, out_empty => s_acq_dma_empty, out_data => s_acq_dma_data ); -- Capture digital inputs. s_dig_in(0) <= exp_p_io(0); s_dig_in(1) <= exp_n_io(0); s_dig_in(2) <= exp_p_io(1); s_dig_in(3) <= exp_n_io(1); inst_dig_capture_gen: for i in 0 to 3 generate -- Use a 2-flipflop synchronizer to avoid metastability. inst_dig_sync: entity work.syncdff port map ( clk => clk_adc, di => s_dig_in(i), do => s_dig_sync(i) ); -- Deglitch filter. inst_dig_deglitch: entity work.deglitch generic map ( deglitch_cycles => 4 ) port map ( clk => clk_adc, din => s_dig_sync(i), dout => s_dig_deglitch(i) ); end generate; -- Optionally generate simulated digital signals. process (clk_adc) is begin if rising_edge(clk_adc) then if s_reg_control.dig_simulate = '1' then s_dig_sample <= s_reg_control.dig_sim_state; else s_dig_sample <= s_dig_deglitch; end if; end if; end process; -- Monitor digital signal state. s_reg_status.dig_sample <= s_dig_sample; -- Time tagger. inst_timetagger: entity work.timetagger port map ( clk => clk_adc, reset => s_reset, channel_en => s_reg_control.timetagger_en, marker => s_reg_control.timetagger_mark, timestamp_in => s_timestamp, dig_sample => s_dig_sample, out_valid => s_tt_dma_valid, out_ready => s_tt_dma_ready, out_empty => s_tt_dma_empty, out_data => s_tt_dma_data ); -- Collect interrupt signals from peripherals and generate interrupt to PS. s_reg_status.irq_pending <= s_irq_pending; s_irq_f2p(0) <= s_reg_control.irq_enable and or_reduce(s_irq_pending); s_irq_f2p(7 downto 1) <= (others => '0'); -- Report reset status via GPIO. process (clk_adc, s_ext_reset_n) is begin if s_ext_reset_n = '0' then r_reset_done <= '0'; elsif rising_edge(clk_adc) then r_reset_done <= not s_reset; end if; end process; -- Blinking LED, 1 Hz. process (clk_adc) is begin if rising_edge(clk_adc) then if s_reset = '1' then r_adcclk_cnt <= (others => '0'); r_adcclk_led <= '0'; elsif r_adcclk_cnt = 62499999 then r_adcclk_cnt <= (others => '0'); r_adcclk_led <= not r_adcclk_led; else r_adcclk_cnt <= r_adcclk_cnt + 1; end if; end if; end process; end architecture;