15 Commits

Author SHA1 Message Date
Oliver Bruendler
6b60029bf7 Repository moved to https://github.com/paulscherrerinstitute/psi_multi_stream_daq 2019-08-02 13:49:50 +02:00
Oliver Bruendler
f5dc56dce5 DEVEL: Use AXI slave from psi_common instead of legacy version 2019-07-22 09:29:01 +02:00
Oliver Bruendler
0a6476d7fd DOC: Removed needless folder level in Dependencies 2019-07-03 10:37:21 +02:00
Oliver Bruendler
a8f4b821bd FEATURE: Added dependency resolution script 2019-07-03 10:33:57 +02:00
Oliver Bruendler
33915d6457 DOC: Generated PDF 2019-06-24 08:25:23 +02:00
Oliver Bruendler
841236f53d DEVEL: Added continuous integration files 2019-06-21 07:26:53 +02:00
Oliver Bruendler
a576b2a7c9 BUGFIX: Remove /* in comments (confuses tools) 2019-06-19 16:45:04 +02:00
Oliver Bruendler
657b22aa9c DOC: Updated documentation for release 2019-06-19 14:57:09 +02:00
Oliver Bruendler
1f551fbac2 BUGFIX: Fix code from bringup 2019-06-19 12:51:01 +02:00
Oliver Bruendler
f80dfbc584 DEVEL: Added driver and related documentation 2019-06-19 09:04:08 +02:00
Oliver Bruendler
828759a5a6 BUGFIX: Bugfixes from bringup 2019-06-18 13:45:09 +02:00
Oliver Bruendler
4399e89830 DEVEL: Made IP Vivado Compatible
- Add ID Ports to axi slave interface
- Simplified some expressions in psi_ms_daq_daq_sm.vhd
2019-06-14 07:52:10 +02:00
Oliver Bruendler
1a75cd16a5 BUGFIX: Added various simplifications to make code synthesizable by Vivado 2019-06-06 18:19:56 +02:00
Oliver Bruendler
388d241783 DEVEL: Moved Tosca component to separate repository 2019-06-06 15:21:48 +02:00
Oliver Bruendler
c409f8ea36 FEATURE: Added AXI implementation and implemented LASTWINn Register 2019-06-06 14:58:49 +02:00
52 changed files with 12 additions and 12498 deletions

6
.gitignore vendored
View File

@@ -1,6 +0,0 @@
#TestSynthesis artifacts
test_syn
#Merge files
*.mrg
*.bak

View File

@@ -1,5 +0,0 @@
## 0.2.0
* Updated according to new library versions after open sourcing
## 0.1.0
* Ready for first tests on HW

View File

@@ -1,37 +0,0 @@
# General Information
## Maintainer
Oliver Bründler [oliver.bruendler@psi.ch]
## Authors
Oliver Bründler [oliver.bruendler@psi.ch]
## Rules
The rules that apply for working in this directory are described in:
[https://git.psi.ch/DigitaleSignalVerarbeitung/Documentation/HwToWorkWithGit/blob/master/GitRules.md](https://git.psi.ch/DigitaleSignalVerarbeitung/Documentation/HwToWorkWithGit/blob/master/GitRules.md)
## Documentation
* [Functional Description](doc/psi_multi_stream_daq.pdf)
## Changelog
See [Changelog](Changelog.md)
# Dependencies
## Library
Directory structure as given below
* BoardSupport
* IFC1210
* [smem\_master](https://git.psi.ch/GFA/Libraries/BoardSupport/IFC1210/smem_master) (not released yet)
* Firmware
* TCL
* [PsiSim](https://github.com/paulscherrerinstitute/PsiSim) (2.0.0 or higher, for development only)
* VHDL
* [psi\_common](https://github.com/paulscherrerinstitute/psi_common) (2.0.0 or higher)
* [psi\_tb](https://github.com/paulscherrerinstitute/psi_tb) (2.0.0 or higher, for development only)
* [**psi\_multi\_stream\_daq**](https://git.psi.ch/GFA/Libraries/Firmware/VHDL/psi_multi_stream_daq)
## External
None

12
RepositoryMoved.md Normal file
View File

@@ -0,0 +1,12 @@
# This Repository was moved
New URL: https://github.com/paulscherrerinstitute/psi_multi_stream_daq
New Link: https://github.com/paulscherrerinstitute/psi_multi_stream_daq
**This movement was part of open-sourcing large parts of the FPGA libraries. So more Repositories may be affected**
Note that only version 1.2.0 and higher are open-sourced for licensing and copyright reasons. Older versions must be accessed using this repository.

Binary file not shown.

Binary file not shown.

Binary file not shown.

View File

@@ -1,299 +0,0 @@
------------------------------------------------------------------------------
-- Libraries
------------------------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_common_array_pkg.all;
use work.smem_master_types_pkg.all;
use work.psi_ms_daq_pkg.all;
------------------------------------------------------------------------------
-- Entity Declaration
------------------------------------------------------------------------------
entity psi_ms_daq is
generic (
Streams_g : positive range 1 to 32 := 2;
StreamWidth_g : t_ainteger := (16, 16);
StreamPrio_g : t_ainteger := (1, 1);
StreamBuffer_g : t_ainteger := (1024, 1024);
StreamTimeout_g : t_areal := (1.0e-3, 1.0e-3);
StreamClkFreq_g : t_areal := (100.0e6, 100.0e6);
StreamTsFifoDepth_g : t_ainteger := (16, 16);
StreamUseTs_g : t_abool := (true, true);
MaxWindows_g : positive range 1 to 32 := 16;
MinBurstSize_g : integer := 512;
MaxBurstSize_g : integer := 512
);
port (
-- Data Stream Input
Str_Clk : in std_logic_vector(Streams_g-1 downto 0);
Str_Data : in t_aslv64(Streams_g-1 downto 0);
Str_Ts : in t_aslv64(Streams_g-1 downto 0);
Str_Vld : in std_logic_vector(Streams_g-1 downto 0);
Str_Rdy : out std_logic_vector(Streams_g-1 downto 0);
Str_Trig : in std_logic_vector(Streams_g-1 downto 0);
-- TMEM Interface
Tmem_Clk : in std_logic;
Tmem_Rst : in std_logic;
TmemAcq : in TmemRqst_t;
AcqTmem : out TmemResp_t;
-- SMEM Interface
Smem_Clk : in std_logic;
Smem_Rst : in std_logic;
AcqSmem : out ToSmemWr_t;
SmemAcq : in FromSmemWr_t;
-- Miscellaneous
Irq : out std_logic -- TMEM clock domain
);
end entity;
------------------------------------------------------------------------------
-- Architecture Declaration
------------------------------------------------------------------------------
architecture rtl of psi_ms_daq is
-- Control Signals
signal Rst : std_logic;
-- Input/Statemachine Signals
signal InpSm_HasTlast : std_logic_vector(Streams_g-1 downto 0);
signal InpSm_TsVld : std_logic_vector(Streams_g-1 downto 0);
signal InpSm_TsRdy : std_logic_vector(Streams_g-1 downto 0);
signal InpSm_Level : t_aslv16(Streams_g-1 downto 0);
signal InpSm_TsData : t_aslv64(Streams_g-1 downto 0);
-- Statemachine/Dma
signal SmDma_Cmd : DaqSm2DaqDma_Cmd_t;
signal SmDma_CmdVld : std_logic;
signal DmaSm_Resp : DaqDma2DaqSm_Resp_t;
signal DmaSm_RespVld : std_logic;
signal DmaSm_RespRdy : std_logic;
signal DmaSm_HasLast : std_logic_vector(Streams_g-1 downto 0);
-- Input/Dma
signal InpDma_Vld : std_logic_vector(Streams_g-1 downto 0);
signal InpDma_Rdy : std_logic_vector(Streams_g-1 downto 0);
signal InpDma_Data : Input2Daq_Data_a(Streams_g-1 downto 0);
-- Dma/Mem
signal DmaMem_CmdAddr : std_logic_vector(31 downto 0);
signal DmaMem_CmdSize : std_logic_vector(31 downto 0);
signal DmaMem_CmdVld : std_logic;
signal DmaMem_CmdRdy : std_logic;
signal DmaMem_DatData : std_logic_vector(63 downto 0);
signal DmaMem_DatVld : std_logic;
signal DmaMem_DatRdy : std_logic;
-- Mem/Statemachine
signal MemSm_Done : std_logic;
-- Configuration
signal Cfg_StrEna : std_logic_vector(Streams_g-1 downto 0);
signal Cfg_GlbEna : std_logic;
signal Cfg_PostTrig : t_aslv32(Streams_g-1 downto 0);
signal Cfg_Arm : std_logic_vector(Streams_g-1 downto 0);
signal Cfg_RecMode : t_aslv2(Streams_g-1 downto 0);
-- Status
signal Stat_StrIrq : std_logic_vector(Streams_g-1 downto 0);
signal Stat_IsArmed : std_logic_vector(Streams_g-1 downto 0);
signal Stat_IsRecording : std_logic_vector(Streams_g-1 downto 0);
-- Context Memory Connections
signal CtxStr_Cmd : ToCtxStr_t;
signal CtxStr_Resp : FromCtx_t;
signal CtxWin_Cmd : ToCtxWin_t;
signal CtxWin_Resp : FromCtx_t;
-- Others
signal Sm_HasLast : std_logic_vector(Streams_g-1 downto 0);
begin
--------------------------------------------
-- TMEM Interface
--------------------------------------------
i_reg : entity work.psi_ms_daq_reg_tmem
generic map (
Streams_g => Streams_g,
MaxWindows_g => MaxWindows_g
)
port map (
ClkTmem => Tmem_Clk,
RstTmem => Tmem_Rst,
TmemRqst => TmemAcq,
TmemResp => AcqTmem,
IrqOut => Irq,
PostTrig => Cfg_PostTrig,
Arm => Cfg_Arm,
IsArmed => Stat_IsArmed,
IsRecording => Stat_IsRecording,
RecMode => Cfg_RecMode,
ClkSmem => Smem_Clk,
RstSmem => Smem_Rst,
CtxStr_Cmd => CtxStr_Cmd,
CtxStr_Resp => CtxStr_Resp,
CtxWin_Cmd => CtxWin_Cmd,
CtxWin_Resp => CtxWin_Resp,
InLevel => InpSm_Level,
StrIrq => Stat_StrIrq,
StrEna => Cfg_StrEna,
GlbEna => Cfg_GlbEna
);
--------------------------------------------
-- Input Logic Instantiation
--------------------------------------------
g_input : for str in 0 to Streams_g-1 generate
signal InRst : std_logic;
signal StrInput : std_logic_vector(StreamWidth_g(str)-1 downto 0);
begin
-- Reset if stream is disabled
InRst <= Smem_Rst or not Cfg_StrEna(str) or not Cfg_GlbEna;
StrInput <= Str_Data(str)(StrInput'range);
-- Instantiation
i_input : entity work.psi_ms_daq_input
generic map (
StreamWidth_g => StreamWidth_g(str),
StreamBuffer_g => StreamBuffer_g(str),
StreamTimeout_g => StreamTimeout_g(str),
StreamClkFreq_g => StreamClkFreq_g(str),
StreamTsFifoDepth_g => StreamTsFifoDepth_g(str),
StreamUseTs_g => StreamUseTs_g(str)
)
port map (
Str_Clk => Str_Clk(str),
Str_Vld => Str_Vld(str),
Str_Rdy => Str_Rdy(str),
Str_Data => StrInput,
Str_Trig => Str_Trig(str),
Str_Ts => Str_Ts(str),
ClkTmem => Tmem_Clk,
RstTmem => Tmem_Rst,
PostTrigSpls => Cfg_PostTrig(str),
Mode => Cfg_RecMode(str),
Arm => Cfg_Arm(str),
IsArmed => Stat_IsArmed(str),
IsRecording => Stat_IsRecording(str),
ClkSmem => Smem_Clk,
RstSmem => InRst,
Daq_Vld => InpDma_Vld(str),
Daq_Rdy => InpDma_Rdy(str),
Daq_Data => InpDma_Data(str),
Daq_Level => InpSm_Level(str),
Daq_HasLast => InpSm_HasTlast(str),
Ts_Vld => InpSm_TsVld(str),
Ts_Rdy => InpSm_TsRdy(str),
Ts_Data => InpSm_TsData(str)
);
end generate;
--------------------------------------------
-- Control State Machine
--------------------------------------------
-- Detect end-of frame in input buffer or DMA buffer
Sm_HasLast <= InpSm_HasTlast or DmaSm_HasLast;
-- Instantiation
i_statemachine : entity work.psi_ms_daq_daq_sm
generic map (
Streams_g => Streams_g,
StreamPrio_g => StreamPrio_g,
StreamWidth_g => StreamWidth_g,
Windows_g => MaxWindows_g,
MinBurstSize_g => MinBurstSize_g,
MaxBurstSize_g => MaxBurstSize_g
)
port map (
Clk => Smem_Clk,
Rst => Smem_Rst,
GlbEna => Cfg_GlbEna,
StrEna => Cfg_StrEna,
StrIrq => Stat_StrIrq,
Inp_HasLast => Sm_HasLast,
Inp_Level => InpSm_Level,
Ts_Vld => InpSm_TsVld,
Ts_Rdy => InpSm_TsRdy,
Ts_Data => InpSm_TsData,
Dma_Cmd => SmDma_Cmd,
Dma_Cmd_Vld => SmDma_CmdVld,
Dma_Resp => DmaSm_Resp,
Dma_Resp_Vld => DmaSm_RespVld,
Dma_Resp_Rdy => DmaSm_RespRdy,
TfDone => MemSm_Done,
-- Context RAM connections
CtxStr_Cmd => CtxStr_Cmd,
CtxStr_Resp => CtxStr_Resp,
CtxWin_Cmd => CtxWin_Cmd,
CtxWin_Resp => CtxWin_Resp
);
--------------------------------------------
-- DMA Engine
--------------------------------------------
i_dma : entity work.psi_ms_daq_daq_dma
generic map (
Streams_g => Streams_g
)
port map (
Clk => Smem_Clk,
Rst => Smem_Rst,
DaqSm_Cmd => SmDma_Cmd,
DaqSm_Cmd_Vld => SmDma_CmdVld,
DaqSm_Resp => DmaSm_Resp,
DaqSm_Resp_Vld => DmaSm_RespVld,
DaqSm_Resp_Rdy => DmaSm_RespRdy,
DaqSm_HasLast => DmaSm_HasLast,
Inp_Vld => InpDma_Vld,
Inp_Rdy => InpDma_Rdy,
Inp_Data => InpDma_Data,
Mem_CmdAddr => DmaMem_CmdAddr,
Mem_CmdSize => DmaMem_CmdSize,
Mem_CmdVld => DmaMem_CmdVld,
Mem_CmdRdy => DmaMem_CmdRdy,
Mem_DatData => DmaMem_DatData,
Mem_DatVld => DmaMem_DatVld,
Mem_DatRdy => DmaMem_DatRdy
);
--------------------------------------------
-- SMEM Controller
--------------------------------------------
i_memif : entity work.smem_master_write
generic map (
MaxBurstSize_g => 512,
MemBlockSize_g => 4096,
DataBufferSize_g => 1024,
MaxOpenTransactions_g => Streams_g
)
port map (
Clk => Smem_Clk,
Rst => Smem_Rst,
Cmd_Addr => DmaMem_CmdAddr,
Cmd_Size => DmaMem_CmdSize,
Cmd_Vld => DmaMem_CmdVld,
Cmd_Rdy => DmaMem_CmdRdy,
Dat_Data => DmaMem_DatData,
Dat_Vld => DmaMem_DatVld,
Dat_Rdy => DmaMem_DatRdy,
Done => MemSm_Done,
ToSmem => AcqSmem,
FromSmem => SmemAcq
);
end;

View File

@@ -1,390 +0,0 @@
------------------------------------------------------------------------------
-- Description
------------------------------------------------------------------------------
-- This component calculates a binary division of two fixed point values.
------------------------------------------------------------------------------
-- Libraries
------------------------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_common_logic_pkg.all;
use work.psi_common_array_pkg.all;
use work.psi_ms_daq_pkg.all;
------------------------------------------------------------------------------
-- Entity Declaration
------------------------------------------------------------------------------
-- $$ testcases=aligned,unaligned,no_data_read,input_empty,empty_timeout,cmd_full,data_full,errors $$
-- $$ processes=control,input,mem_cmd,mem_dat $$
-- $$ tbpkg=work.psi_tb_txt_util,work.psi_tb_compare_pkg,work.psi_tb_activity_pkg $$
entity psi_ms_daq_daq_dma is
generic (
Streams_g : positive range 1 to 32 := 4 -- $$ constant=4 $$
);
port (
-- Control signals
Clk : in std_logic; -- $$ type=clk; freq=200e6; proc=control,input,mem_dat,mem_cmd $$
Rst : in std_logic; -- $$ type=rst; clk=Clk; proc=control $$
-- DAQ Statemachione Connections
DaqSm_Cmd : in DaqSm2DaqDma_Cmd_t; -- $$ proc=control $$
DaqSm_Cmd_Vld : in std_logic; -- $$ proc=control $$
DaqSm_Resp : out DaqDma2DaqSm_Resp_t; -- $$ proc=control $$
DaqSm_Resp_Vld : out std_logic; -- $$ proc=control $$
DaqSm_Resp_Rdy : in std_logic; -- $$ proc=control $$
DaqSm_HasLast : out std_logic_vector(Streams_g-1 downto 0); -- $$ proc=control $$
-- Input handling connections
Inp_Vld : in std_logic_vector(Streams_g-1 downto 0); -- $$ proc=input $$
Inp_Rdy : out std_logic_vector(Streams_g-1 downto 0); -- $$ proc=input $$
Inp_Data : in Input2Daq_Data_a(Streams_g-1 downto 0); -- $$ proc=input $$
-- Memory interface connections
Mem_CmdAddr : out std_logic_vector(31 downto 0); -- $$ proc=mem_cmd $$
Mem_CmdSize : out std_logic_vector(31 downto 0); -- $$ proc=mem_cmd $$
Mem_CmdVld : out std_logic; -- $$ proc=mem_cmd $$
Mem_CmdRdy : in std_logic; -- $$ proc=mem_cmd $$
Mem_DatData : out std_logic_vector(63 downto 0); -- $$ proc=mem_dat $$
Mem_DatVld : out std_logic; -- $$ proc=mem_dat $$
Mem_DatRdy : in std_logic -- $$ proc=mem_dat $$
);
end entity;
------------------------------------------------------------------------------
-- Architecture Declaration
------------------------------------------------------------------------------
architecture rtl of psi_ms_daq_daq_dma is
-- Constants
constant BufferFifoDepth_c : integer := 32;
-- Component Connection Signals
signal CmdFifo_Level_Dbg : std_logic_vector(log2ceil(Streams_g) downto 0);
signal CmdFifo_InData : std_logic_vector(DaqSm2DaqDma_Cmd_Size_c-1 downto 0);
signal CmdFifo_OutData : std_logic_vector(DaqSm2DaqDma_Cmd_Size_c-1 downto 0);
signal CmdFifo_Cmd : DaqSm2DaqDma_Cmd_t;
signal CmdFifo_Vld : std_logic;
signal RspFifo_Level_Dbg : std_logic_vector(log2ceil(Streams_g) downto 0);
signal RspFifo_InData : std_logic_vector(DaqDma2DaqSm_Resp_Size_c-1 downto 0);
signal RspFifo_OutData : std_logic_vector(DaqDma2DaqSm_Resp_Size_c-1 downto 0);
signal DatFifo_Level_Dbg : std_logic_vector(log2ceil(BufferFifoDepth_c) downto 0);
signal DatFifo_AlmFull : std_logic;
signal Rem_RdBytes : std_logic_vector(2 downto 0);
signal Rem_Data : std_logic_vector(63 downto 0);
signal Rem_Trigger : std_logic;
signal Rem_Last : std_logic;
-- Types
type State_t is (Idle_s, RemRd1_s, RemRd2_s, Transfer_s, Done_s, Cmd_s);
-- Two process method
type two_process_r is record
CmdFifo_Rdy : std_logic;
RspFifo_Vld : std_logic;
RspFifo_Data : DaqDma2DaqSm_Resp_t;
Mem_DataVld : std_logic;
StreamStdlv : std_logic_vector(log2ceil(Streams_g)-1 downto 0);
RemWen : std_logic;
RemWrBytes : std_logic_vector(2 downto 0);
RemData : std_logic_vector(63 downto 0);
RemTrigger : std_logic;
RemLast : std_logic;
RemWrTrigger : std_logic;
RemWrLast : std_logic;
State : State_t;
HndlMaxSize : unsigned(15 downto 0);
RdBytes : unsigned(15 downto 0);
WrBytes : unsigned(15 downto 0);
HndlStream : integer range 0 to MaxStreams_c-1;
HndlAddress : std_logic_vector(31 downto 0);
UpdateLast : std_logic;
HndlSft : unsigned(2 downto 0);
FirstDma : std_logic_vector(Streams_g-1 downto 0);
Mem_CmdVld : std_logic;
Trigger : std_logic;
Last : std_logic;
DataSft : std_logic_vector(127 downto 0);
NextDone : std_logic;
DataWritten : std_logic;
HasLast : std_logic_vector(Streams_g-1 downto 0);
end record;
signal r, r_next : two_process_r;
begin
--------------------------------------------
-- Combinatorial Process
--------------------------------------------
p_comb : process( r, DaqSm_Cmd, DaqSm_Cmd_Vld, DaqSm_Resp_Rdy, Inp_Vld, Inp_Data, Mem_CmdRdy, Mem_DatRdy,
CmdFifo_Cmd, CmdFifo_Vld, DatFifo_AlmFull, Rem_RdBytes, Rem_Data, Rem_Trigger, Rem_Last)
variable v : two_process_r;
variable ThisByte_v : std_logic_vector(7 downto 0);
variable RemSft_v : integer range 0 to 7;
begin
-- *** Hold variables stable ***
v := r;
-- *** Default Values ***
v.CmdFifo_Rdy := '0';
Inp_Rdy <= (others => '0');
v.Mem_DataVld := '0';
v.RspFifo_Vld := '0';
v.RemWen := '0';
v.UpdateLast := '0';
-- *** State Machine ***
case r.State is
when Idle_s =>
v.HndlMaxSize := unsigned(CmdFifo_Cmd.MaxSize);
v.HndlStream := CmdFifo_Cmd.Stream;
v.StreamStdlv := std_logic_vector(to_unsigned(CmdFifo_Cmd.Stream, v.StreamStdlv'length));
v.HndlAddress := CmdFifo_Cmd.Address;
v.Trigger := '0';
v.Last := '0';
if CmdFifo_Vld = '1' then
v.CmdFifo_Rdy := '1';
v.State := RemRd1_s;
end if;
when RemRd1_s =>
v.State := RemRd2_s;
when RemRd2_s =>
-- Prevent RAM data from before reset to have an influence
v.WrBytes := (others => '0');
if r.FirstDma(r.HndlStream) = '1' then
v.HndlSft := (others => '0');
v.RdBytes := (others => '0');
v.DataSft := (others => '0');
v.RemTrigger := '0';
v.RemLast := '0';
else
v.HndlSft := unsigned(Rem_RdBytes);
v.DataSft(127 downto 64) := Rem_Data;
v.RdBytes := resize(unsigned(Rem_RdBytes), v.RdBytes'length);
v.RemTrigger := Rem_Trigger;
v.RemLast := Rem_Last;
end if;
v.FirstDma(r.HndlStream) := '0';
v.State := Transfer_s;
v.NextDone := '0';
v.DataWritten := '0';
when Transfer_s =>
-- TF done because of maximum size reached
if r.WrBytes >= r.HndlMaxSize then
v.State := Done_s;
elsif DatFifo_AlmFull = '0' then
if r.NextDone = '0' and Inp_Vld(r.HndlStream) = '1' and r.RemLast = '0' then
v.RdBytes := r.RdBytes + unsigned(Inp_Data(r.HndlStream).Bytes);
end if;
v.WrBytes := r.WrBytes + 8;
-- Combinatorial handling because of fall-through interface at input
if r.RdBytes < r.HndlMaxSize and r.NextDone = '0' and r.RemLast = '0' then
Inp_Rdy(r.HndlStream) <= '1';
end if;
-- Handling of last frame
if (Inp_Data(r.HndlStream).Last = '1') or (r.RemLast = '1') then
-- Do one more word if not all data can be transferred in the current beat (NextDone = 1)
if (r.HndlSft + unsigned(Inp_Data(r.HndlStream).Bytes) <= 8) or (r.RemLast = '1') then
v.State := Done_s;
else
v.NextDone := '1';
end if;
if (Inp_Data(r.HndlStream).IsTrig = '1') or (r.RemTrigger = '1') then
v.Trigger :='1';
end if;
v.Last := '1';
end if;
if r.NextDone = '1' or Inp_Vld(r.HndlStream) = '0' then
v.State := Done_s;
end if;
-- Data handling
v.DataSft(63 downto 0) := r.DataSft(127 downto 64);
v.DataSft(8*to_integer(r.HndlSft)+63 downto 8*to_integer(r.HndlSft)) := Inp_Data(r.HndlStream).Data;
if Inp_Vld(r.HndlStream) = '1' or r.HndlSft /= 0 then
v.Mem_DataVld := '1';
v.DataWritten := '1';
end if;
end if;
when Done_s =>
RemSft_v := to_integer(resize(r.HndlMaxSize, 3));
v.RemWrTrigger := '0';
v.RemWrLast := '0';
if r.HndlMaxSize < r.RdBytes then
v.RemWrBytes := std_logic_vector(resize(r.RdBytes - r.HndlMaxSize, v.RemWrBytes'length));
v.RdBytes := r.HndlMaxSize;
v.RemWrTrigger := r.Trigger;
v.RemWrLast := r.Last;
v.HasLast(r.HndlStream) := r.Last;
else
v.RemWrBytes := (others => '0');
v.HasLast(r.HndlStream) := '0';
end if;
v.RemData := v.DataSft(8*RemSft_v+63 downto 8*RemSft_v);
v.State := Cmd_s;
if r.DataWritten = '1' then
v.Mem_CmdVld := '1';
end if;
v.RemWen := '1';
when Cmd_s =>
if Mem_CmdRdy = '1' or r.Mem_CmdVld = '0' then
v.State := Idle_s;
v.Mem_CmdVld := '0';
v.RspFifo_Vld := '1';
v.RspFifo_Data.Size := std_logic_vector(r.RdBytes);
-- Only mark as trigger if all samples are completely written to memory (no remaining samples in REM RAM)
if (unsigned(r.RemWrBytes) = 0) and (r.Trigger = '1') then
v.RspFifo_Data.Trigger := '1';
else
v.RspFifo_Data.Trigger := '0';
end if;
v.RspFifo_Data.Stream := r.HndlStream;
end if;
when others => null;
end case;
-- *** Assign to signal ***
r_next <= v;
end process;
-- *** Registered Outputs ***
Mem_CmdAddr <= r.HndlAddress;
Mem_CmdSize(r.RdBytes'range) <= std_logic_vector(r.RdBytes);
Mem_CmdSize(Mem_CmdSize'high downto r.RdBytes'high+1) <= (others => '0');
Mem_CmdVld <= r.Mem_CmdVld;
DaqSm_HasLast <= r.HasLast;
--------------------------------------------
-- Sequential Process
--------------------------------------------
p_seq : process(Clk)
begin
if rising_edge(Clk) then
r <= r_next;
if Rst = '1' then
r.CmdFifo_Rdy <= '0';
r.RspFifo_Vld <= '0';
r.Mem_DataVld <= '0';
r.RemWen <= '0';
r.State <= Idle_s;
r.FirstDma <= (others => '1');
r.Mem_CmdVld <= '0';
r.HasLast <= (others => '0');
end if;
end if;
end process;
--------------------------------------------
-- Component Instantiation
--------------------------------------------
-- *** Command FIFO ***
CmdFifo_InData <= DaqSm2DaqDma_Cmd_ToStdlv(DaqSm_Cmd);
i_fifocmd : entity work.psi_common_sync_fifo
generic map (
Width_g => DaqSm2DaqDma_Cmd_Size_c,
Depth_g => Streams_g,
RamStyle_g => "distributed",
RamBehavior_g => "RBW"
)
port map (
Clk => Clk,
Rst => Rst,
InData => CmdFifo_InData,
InVld => DaqSm_Cmd_Vld,
OutData => CmdFifo_OutData,
OutVld => CmdFifo_Vld,
OutRdy => r.CmdFifo_Rdy,
OutLevel => CmdFifo_Level_Dbg
);
CmdFifo_Cmd <= DaqSm2DaqDma_Cmd_FromStdlv(CmdFifo_OutData);
-- *** Response FIFO ***
-- Ready not required for system reasons: There is never more commands open than streams.
RspFifo_InData <= DaqDma2DaqSm_Resp_ToStdlv(r.RspFifo_Data);
i_fiforsp : entity work.psi_common_sync_fifo
generic map (
Width_g => DaqDma2DaqSm_Resp_Size_c,
Depth_g => Streams_g,
RamStyle_g => "distributed",
RamBehavior_g => "RBW"
)
port map (
Clk => Clk,
Rst => Rst,
InData => RspFifo_InData,
InVld => r.RspFifo_Vld,
OutData => RspFifo_OutData,
OutVld => DaqSm_Resp_Vld,
OutRdy => DaqSm_Resp_Rdy,
OutLevel => RspFifo_Level_Dbg
);
DaqSm_Resp <= DaqDme2DaqSm_Resp_FromStdlv(RspFifo_OutData);
-- *** Buffer FIFO ***
-- This FIFO allows buffering data for the time the state machine requires to react on a "memory interface not ready for more data" situation.
-- As a result, the backpressure must not handled in the complete pipeline of this block.
-- Rdy is not required since the data pipeline is stopped based on the almost full flag
i_fifodata : entity work.psi_common_sync_fifo
generic map (
Width_g => 64,
Depth_g => BufferFifoDepth_c,
AlmFullOn_g => true,
AlmFullLevel_g => BufferFifoDepth_c/2,
RamStyle_g => "distributed",
RamBehavior_g => "RBW"
)
port map (
Clk => Clk,
Rst => Rst,
InData => r.DataSft(63 downto 0),
InVld => r.Mem_DataVld,
OutData => Mem_DatData,
OutVld => Mem_DatVld,
OutRdy => Mem_DatRdy,
OutLevel => DatFifo_Level_Dbg,
AlmFull => DatFifo_AlmFull
);
-- *** Remaining Data RAM ***
i_remram : entity work.psi_common_sdp_ram
generic map (
Depth_g => Streams_g,
Width_g => 1+1+3+64,
IsAsync_g => false,
RamStyle_g => "distributed",
Behavior_g => "RBW"
)
port map (
Clk => Clk,
RdClk => Rst,
WrAddr => r.StreamStdlv,
Wr => r.RemWen,
WrData(68) => r.RemWrLast,
WrData(67) => r.RemWrTrigger,
WrData(66 downto 64) => r.RemWrBytes,
WrData(63 downto 0) => r.RemData,
RdAddr => r.StreamStdlv,
RdDAta(68) => Rem_Last,
RdData(67) => Rem_Trigger,
RdData(66 downto 64) => Rem_RdBytes,
RdData(63 downto 0) => Rem_Data
);
end;

View File

@@ -1,680 +0,0 @@
------------------------------------------------------------------------------
-- Description
------------------------------------------------------------------------------
-- This component calculates a binary division of two fixed point values.
------------------------------------------------------------------------------
-- Libraries
------------------------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_common_logic_pkg.all;
use work.psi_common_array_pkg.all;
use work.psi_ms_daq_pkg.all;
------------------------------------------------------------------------------
-- Entity Declaration
------------------------------------------------------------------------------
-- $$ testcases=single_simple,priorities,single_window,multi_window,enable,irq,timestamp $$
-- $$ processes=control,dma_cmd,dma_resp,ctx $$
-- $$ tbpkg=work.psi_tb_txt_util,work.psi_tb_compare_pkg $$
entity psi_ms_daq_daq_sm is
generic (
Streams_g : positive range 1 to 32 := 4; -- $$ constant=4 $$
StreamPrio_g : t_ainteger := (1, 2, 3, 1); -- $$ constant=(1, 2, 3, 1) $$
StreamWidth_g : t_ainteger := (8, 16, 32, 64); -- $$ constant=(8, 16, 32, 64) $$
Windows_g : positive range 1 to 32 := 4; -- $$ constant=4 $$
MinBurstSize_g : positive := 512; -- $$ constant=512 $$
MaxBurstSize_g : positive := 512 -- $$ constant=512 $$
);
port (
-- Control signals
Clk : in std_logic; -- $$ type=clk; freq=200e6; proc=control,dma_cmd,dma_resp,ctx $$
Rst : in std_logic; -- $$ proc=control $$
GlbEna : in std_logic; -- $$ proc=control; lowactive=true $$
StrEna : in std_logic_vector(Streams_g-1 downto 0); -- $$ proc=control; lowactive=true $$
StrIrq : out std_logic_vector(Streams_g-1 downto 0); -- $$ proc=control,dma_resp,dma_cmd; $$
-- Input logic Connections
Inp_HasLast : in std_logic_vector(Streams_g-1 downto 0); -- $$ proc=control $$
Inp_Level : in t_aslv16(Streams_g-1 downto 0); -- $$ proc=control $$
Ts_Vld : in std_logic_vector(Streams_g-1 downto 0); -- $$ proc=control $$
Ts_Rdy : out std_logic_vector(Streams_g-1 downto 0); -- $$ proc=control $$
Ts_Data : in t_aslv64(Streams_g-1 downto 0); -- $$ proc=control $$
-- Dma Connections
Dma_Cmd : out DaqSm2DaqDma_Cmd_t; -- $$ proc=dma_cmd,control $$
Dma_Cmd_Vld : out std_logic; -- $$ proc=dma_cmd,control $$
Dma_Resp : in DaqDma2DaqSm_Resp_t; -- $$ proc=dma_resp $$
Dma_Resp_Vld : in std_logic; -- $$ proc=dma_resp $$
Dma_Resp_Rdy : out std_logic; -- $$ proc=dma_resp $$
-- Memory Controller
TfDone : in std_logic; -- $$ proc=dma_resp $$
-- Context RAM connections
CtxStr_Cmd : out ToCtxStr_t; -- $$ proc=ctx $$
CtxStr_Resp : in FromCtx_t; -- $$ proc=ctx $$
CtxWin_Cmd : out ToCtxWin_t; -- $$ proc=ctx $$
CtxWin_Resp : in FromCtx_t -- $$ proc=ctx $$
);
end entity;
------------------------------------------------------------------------------
-- Architecture Declaration
------------------------------------------------------------------------------
architecture rtl of psi_ms_daq_daq_sm is
-- Function Definitions
function GetBitsOfStreamPrio( InputVector : std_logic_vector;
Prio : integer)
return std_logic_vector is
variable Result_v : std_logic_vector(count(StreamPrio_g, Prio)-1 downto 0);
variable OutIdx_v : integer := 0;
begin
for idx in InputVector'low to InputVector'high loop
if StreamPrio_g(idx) = Prio then
Result_v(OutIdx_v) := InputVector(idx);
OutIdx_v := OutIdx_v + 1;
end if;
end loop;
return Result_v;
end function;
function GetStreamNrFromGrant( GrantVector : std_logic_vector;
Prio : integer)
return integer is
variable IdxCnt_v : integer := 0;
begin
for idx in StreamPrio_g'low to StreamPrio_g'high loop
if StreamPrio_g(idx) = Prio then
if GrantVector(IdxCnt_v) = '1' then
return idx;
end if;
IdxCnt_v := IdxCnt_v + 1;
end if;
end loop;
return 0;
end function;
-- Component Connection Signals
signal AvailPrio1 : std_logic_vector(count(StreamPrio_g, 1)-1 downto 0);
signal AvailPrio2 : std_logic_vector(count(StreamPrio_g, 2)-1 downto 0);
signal AvailPrio3 : std_logic_vector(count(StreamPrio_g, 3)-1 downto 0);
signal GrantPrio1 : std_logic_vector(AvailPrio1'range);
signal GrantPrio2 : std_logic_vector(AvailPrio2'range);
signal GrantPrio3 : std_logic_vector(AvailPrio3'range);
signal GrantVld : std_logic_vector(3 downto 1);
signal IrqFifoAlmFull : std_logic;
signal IrqFifoEmpty : std_logic;
signal IrqFifoGenIrq : std_logic;
signal IrqFifoStream : std_logic_vector(log2ceil(Streams_g)-1 downto 0);
signal IrqFifoIn : std_logic_vector(log2ceil(Streams_g) downto 0);
signal IrqFifoOut : std_logic_vector(log2ceil(Streams_g) downto 0);
-- Types
type State_t is (Idle_s, CheckPrio1_s, CheckPrio2_s, CheckPrio3_s, CheckResp_s, TlastCheck_s, ReadCtxStr_s, First_s, ReadCtxWin_s, CalcAccess0_s, CalcAccess1_s, ProcResp0_s, NextWin_s, WriteCtx_s);
-- Two process method
type two_process_r is record
GlbEnaReg : std_logic;
StrEnaReg : std_logic_vector(Streams_g-1 downto 0);
InpDataAvail : std_logic_vector(Streams_g-1 downto 0);
DataAvailArbIn : std_logic_vector(Streams_g-1 downto 0);
DataPending : std_logic_vector(Streams_g-1 downto 0);
OpenCommand : std_logic_vector(Streams_g-1 downto 0);
WinProtected : std_logic_vector(Streams_g-1 downto 0); -- Set if the current window is not yet available
NewBuffer : std_logic_vector(Streams_g-1 downto 0);
FirstAfterEna : std_logic_vector(Streams_g-1 downto 0);
FirstOngoing : std_logic_vector(Streams_g-1 downto 0);
GrantVldReg : std_logic_vector(3 downto 1);
State : State_t;
GrantPrio1Reg : std_logic_vector(GrantPrio1'range);
GrantPrio2Reg : std_logic_vector(GrantPrio2'range);
GrantPrio3Reg : std_logic_vector(GrantPrio3'range);
HasLastReg : std_logic_vector(Inp_HasLast'range);
HndlAfterCtxt : State_t;
HndlStream : integer range 0 to Streams_g;
HndlCtxCnt : integer range 0 to 4;
HndlRingbuf : std_logic;
HndlOverwrite : std_logic;
HndlWincnt : std_logic_vector(log2ceil(Windows_g)-1 downto 0);
HndlWincur : std_logic_vector(log2ceil(Windows_g)-1 downto 0);
HndlBufstart : std_logic_vector(31 downto 0);
HndlWinSize : std_logic_vector(31 downto 0);
HndlPtr0 : std_logic_vector(31 downto 0);
HndlPtr1 : std_logic_vector(31 downto 0);
HndlPtr2 : std_logic_vector(31 downto 0);
HndlLevel : std_logic_vector(15 downto 0);
Hndl4kMax : std_logic_vector(12 downto 0);
HndlWinMax : std_logic_vector(31 downto 0);
HndlWinEnd : std_logic_vector(31 downto 0);
HndlWinBytes : std_logic_vector(32 downto 0);
HndlWinLast : std_logic_vector(31 downto 0);
HndlTs : std_logic_vector(63 downto 0);
TfDoneCnt : std_logic_vector(log2ceil(Streams_g)-1 downto 0);
TfDoneReg : std_logic;
HndlWinDone : std_logic;
CtxStr_Cmd : ToCtxStr_t;
CtxWin_Cmd : ToCtxWin_t;
Dma_Cmd : DaqSm2DaqDma_Cmd_t;
Dma_Cmd_Vld : std_logic;
Dma_Resp_Rdy : std_logic;
Ts_Rdy : std_logic_vector(Streams_g-1 downto 0);
ArbDelCnt : integer range 0 to 4;
IrqFifoWrite : std_logic;
IrqFifoRead : std_logic;
StrIrq : std_logic_vector(Streams_g-1 downto 0);
EndByTrig : std_logic;
end record;
signal r, r_next : two_process_r;
-- Todo: mask streams that already have a transfer open at the input
begin
--------------------------------------------
-- Combinatorial Process
--------------------------------------------
p_comb : process( r, Inp_HasLast, Inp_Level, Ts_Vld, Ts_Data, Dma_Resp, Dma_Resp_Vld, CtxStr_Resp, CtxWin_Resp, GlbEna, StrEna, TfDone, IrqFifoGenIrq, IrqFifoStream,
GrantVld, GrantPrio1, GrantPrio2, GrantPrio3, IrqFifoAlmFull, IrqFifoEmpty)
variable v : two_process_r;
begin
-- *** Hold variables stable ***
v := r;
-- *** Default Values ***
v.CtxStr_Cmd.WenLo := '0';
v.CtxStr_Cmd.WenHi := '0';
v.CtxWin_Cmd.WenLo := '0';
v.CtxWin_Cmd.WenHi := '0';
v.CtxStr_Cmd.Rd := '0';
v.CtxWin_Cmd.Rd := '0';
v.Dma_Cmd_Vld := '0';
v.Ts_Rdy := (others => '0');
v.Dma_Resp_Rdy := '0';
v.CtxWin_Cmd.WdatLo := (others => '0');
v.CtxWin_Cmd.WdatHi := (others => '0');
v.CtxStr_Cmd.WdatLo := (others => '0');
v.CtxStr_Cmd.WdatHi := (others => '0');
v.IrqFifoWrite := '0';
v.IrqFifoRead := '0';
v.StrIrq := (others => '0');
-- *** Pure Pipelining (no functional registers) ***
v.GrantVldReg := GrantVld;
v.GrantPrio1Reg := GrantPrio1;
v.GrantPrio2Reg := GrantPrio2;
v.GrantPrio3Reg := GrantPrio3;
v.HasLastReg := Inp_HasLast;
v.StrEnaReg := StrEna;
v.GlbEnaReg := GlbEna;
v.TfDoneReg := TfDone;
-- *** Check Availability of a full burst ***
for str in 0 to Streams_g-1 loop
if unsigned(Inp_Level(str)) >= MinBurstSize_g then
v.InpDataAvail(str) := r.StrEnaReg(str) and r.GlbEnaReg;
else
v.InpDataAvail(str) := '0';
end if;
end loop;
v.DataAvailArbIn := r.InpDataAvail and (not r.OpenCommand) and (not r.WinProtected); -- Do not arbitrate new commands on streams that already have a command
v.DataPending := r.InpDataAvail and (not r.WinProtected); -- Do not prevent lower priority channels from access if the window of a higher priority stream is protected
-- *** Select level of currently handled FIFO ***
v.HndlLevel := Inp_Level(r.HndlStream);
-- *** State Machine ***
case r.State is
-- *** Idle state ***
when Idle_s =>
v.HndlCtxCnt := 0;
v.HndlWinDone := '0';
-- check if data to write is available (only if IRQ FIFO has space for the response for sure)
if IrqFifoAlmFull = '0' then
v.State := CheckPrio1_s;
v.HndlAfterCtxt := CalcAccess0_s;
end if;
-- Delay arbitration in simulation to allow TB to react
if r.ArbDelCnt /= 4 then
v.State := Idle_s;
v.ArbDelCnt := r.ArbDelCnt + 1;
else
v.ArbDelCnt := 0;
end if;
-- *** Check for next stream to handle ***
when CheckPrio1_s =>
-- Handle command if prio 1 data is available
if r.GrantVldReg(1) = '1' then
v.State := ReadCtxStr_s;
v.HndlStream := GetStreamNrFromGrant(r.GrantPrio1Reg, 1);
-- If data is still pending, check for responses to schedule next transfer
elsif unsigned(GetBitsOfStreamPrio(r.DataPending, 1)) /= 0 then
v.State := CheckResp_s;
-- Otherwise check lower priority streams
else
v.State := CheckPrio2_s;
end if;
when CheckPrio2_s =>
-- Handle command if prio 2 data is available
if r.GrantVldReg(2) = '1' then
v.State := ReadCtxStr_s;
v.HndlStream := GetStreamNrFromGrant(r.GrantPrio2Reg, 2);
-- If data is still pending, check for responses to schedule next transfer
elsif unsigned(GetBitsOfStreamPrio(r.DataPending, 2)) /= 0 then
v.State := CheckResp_s;
-- Otherwise check lower priority streams
else
v.State := CheckPrio3_s;
end if;
when CheckPrio3_s =>
-- Handle command if prio 2 data is available
if r.GrantVldReg(3) = '1' then
v.State := ReadCtxStr_s;
v.HndlStream := GetStreamNrFromGrant(r.GrantPrio3Reg, 3);
-- Otherwise check for frame ends
else
v.State := TlastCheck_s;
end if;
when TlastCheck_s =>
v.State := CheckResp_s;
v.WinProtected := (others => '0'); -- No bursts where available on any stream, so all of them were checked and we can retry whether SW emptied a window.
for idx in 0 to Streams_g-1 loop
if (r.HasLastReg(idx) = '1') and (r.OpenCommand(idx) = '0') and (r.WinProtected(idx) = '0') then
v.State := ReadCtxStr_s;
v.HndlStream := idx;
end if;
end loop;
when CheckResp_s =>
-- Handle response if one is pending (less important thandata transer, therefore at the end)
if Dma_Resp_Vld = '1' then
v.State := ReadCtxStr_s;
v.HndlAfterCtxt := ProcResp0_s;
v.HndlStream := Dma_Resp.Stream;
v.EndByTrig := Dma_Resp.Trigger;
else
v.State := Idle_s;
end if;
-- *** Read Context Memory ***
-- Read information from stream memory
when ReadCtxStr_s =>
-- State handling
if r.HndlCtxCnt = 4 then
v.State := First_s;
v.HndlCtxCnt := 0;
else
v.HndlCtxCnt := r.HndlCtxCnt + 1;
end if;
-- Command Assertions
v.CtxStr_Cmd.Stream := r.HndlStream;
case r.HndlCtxCnt is
when 0 => v.CtxStr_Cmd.Sel := CtxStr_Sel_Winend_c;
v.CtxStr_Cmd.Rd := '1';
when 1 => v.CtxStr_Cmd.Sel := CtxStr_Sel_WinsizePtr_c;
v.CtxStr_Cmd.Rd := '1';
when 2 => v.CtxStr_Cmd.Sel := CtxStr_Sel_ScfgBufstart_c;
v.CtxStr_Cmd.Rd := '1';
when others => null;
end case;
-- Response handling
case r.HndlCtxCnt is
when 2 => v.HndlWinEnd := CtxStr_Resp.RdatLo;
when 3 => v.HndlWinSize := CtxStr_Resp.RdatLo;
v.HndlPtr0 := CtxStr_Resp.RdatHi;
when 4 => v.HndlRingbuf := CtxStr_Resp.RdatLo(CtxStr_Sft_SCFG_RINGBUF_c);
v.HndlOverwrite := CtxStr_Resp.RdatLo(CtxStr_Sft_SCFG_OVERWRITE_c);
v.HndlWincnt := CtxStr_Resp.RdatLo(CtxStr_Sft_SCFG_WINCNT_c+v.HndlWincnt'high downto CtxStr_Sft_SCFG_WINCNT_c);
v.HndlWincur := CtxStr_Resp.RdatLo(CtxStr_Sft_SCFG_WINCUR_c+v.HndlWincur'high downto CtxStr_Sft_SCFG_WINCUR_c);
v.HndlBufstart := CtxStr_Resp.RdatHi;
v.Hndl4kMax := std_logic_vector(to_unsigned(4096, 13) - unsigned(r.HndlPtr0(11 downto 0))); -- Calculate maximum size within this 4k Region
v.HndlWinMax := std_logic_vector(unsigned(r.HndlWinEnd) - unsigned(r.HndlPtr0)); -- Calculate maximum size within this window
when others => null;
end case;
-- Handle first access after enable
when First_s =>
-- State handling
v.State := ReadCtxWin_s;
-- Ensure that command and response are both handled as first or not
if r.HndlAfterCtxt = ProcResp0_s then -- responses
-- nothing to do
else -- command
v.FirstAfterEna(r.HndlStream) := '0';
v.FirstOngoing(r.HndlStream) := r.FirstAfterEna(r.HndlStream);
end if;
-- Update values for first access
if v.FirstOngoing(r.HndlStream) = '1' then
v.HndlWinEnd := std_logic_vector(unsigned(r.HndlBufstart) + unsigned(r.HndlWinSize));
v.HndlPtr0 := r.HndlBufstart;
v.HndlWincur := (others => '0');
v.Hndl4kMax := std_logic_vector(to_unsigned(4096, 13) - unsigned(r.HndlBufstart(11 downto 0)));
v.HndlWinMax := r.HndlWinSize;
end if;
-- Read information from window memory
when ReadCtxWin_s =>
-- State handling
if r.HndlCtxCnt = 2 then
v.State := r.HndlAfterCtxt; -- Goto state depends on the context of the read procedure
else
v.HndlCtxCnt := r.HndlCtxCnt + 1;
end if;
-- Command Assertions
v.CtxWin_Cmd.Stream := r.HndlStream;
v.CtxWin_Cmd.Window := to_integer(unsigned(r.HndlWincur));
case r.HndlCtxCnt is
when 0 => v.CtxWin_Cmd.Sel := CtxWin_Sel_WincntWinlast_c;
v.CtxWin_Cmd.Rd := '1';
when others => null;
end case;
-- Response handling
case r.HndlCtxCnt is
when 2 => v.HndlWinBytes := '0' & ShiftLeft(CtxWin_Resp.RdatLo, log2(StreamWidth_g(r.HndlStream)/8)); -- guard bit required for calculations
when others => null;
end case;
-- *** Calculate next access ***
when CalcAccess0_s =>
-- Calculate Command
v.Dma_Cmd.Address := r.HndlPtr0;
v.Dma_Cmd.Stream := r.HndlStream;
v.Dma_Cmd.MaxSize := std_logic_vector(to_unsigned(MaxBurstSize_g*8, v.Dma_Cmd.MaxSize'length)); -- 8 bytes per 64-bit QWORD
-- State update (abort if window is not free)
if (r.HndlOverwrite = '0') and (unsigned(r.HndlWinBytes) /= 0) and (r.NewBuffer(r.HndlStream) = '1') then
v.State := Idle_s;
v.WinProtected(r.HndlStream) := '1';
else
v.State := CalcAccess1_s;
v.NewBuffer(r.HndlStream) := '0';
-- Mark stream as active
v.OpenCommand(r.HndlStream) := '1';
end if;
when CalcAccess1_s =>
if unsigned(r.Hndl4kMax) < unsigned(r.HndlWinMax) then
if unsigned(r.Dma_Cmd.MaxSize) > unsigned(r.Hndl4kMax) then
v.Dma_Cmd.MaxSize := std_logic_vector(resize(unsigned(r.Hndl4kMax), v.dma_Cmd.MaxSize'length));
end if;
else
if unsigned(r.Dma_Cmd.MaxSize) > unsigned(r.HndlWinMax) then
v.Dma_Cmd.MaxSize := std_logic_vector(resize(unsigned(r.HndlWinMax), v.dma_Cmd.MaxSize'length));
end if;
end if;
v.Dma_Cmd_Vld := '1';
v.State := Idle_s;
-- *** Handle response ***
-- Calculate next pointer
when ProcResp0_s =>
v.OpenCommand(r.HndlStream) := '0';
v.FirstOngoing(r.HndlStream) := '0';
v.HndlPtr1 := std_logic_vector(unsigned(r.HndlPtr0) + unsigned(Dma_Resp.Size));
v.State := NextWin_s;
-- Update window information step 1
v.HndlWinBytes := std_logic_vector(unsigned(r.HndlWinBytes) + unsigned(Dma_Resp.Size));
-- Calculate next window to use
when NextWin_s =>
-- Default Values
v.HndlPtr2 := r.HndlPtr1;
-- Do not wait for "transfer done" for zero size transfers (they are not passed to the memory interface)
if unsigned(Dma_Resp.Size) /= 0 then
v.IrqFifoWrite := '1';
end if;
-- Switch to next window if required
if ((r.HndlPtr1 = r.HndlWinEnd) and (r.HndlRingbuf = '0')) or (Dma_Resp.Trigger = '1') then
v.HndlWinDone := '1';
v.NewBuffer(r.HndlStream) := '1';
if r.HndlWincur = r.HndlWincnt then
v.HndlWincur := (others => '0');
v.HndlPtr2 := r.HndlBufstart;
v.HndlWinEnd := std_logic_vector(unsigned(r.HndlBufstart) + unsigned(r.HndlWinSize));
else
v.HndlWincur := std_logic_vector(unsigned(r.HndlWincur) + 1);
v.HndlPtr2 := r.HndlWinEnd;
v.HndlWinEnd := std_logic_vector(unsigned(r.HndlWinEnd) + unsigned(r.HndlWinSize));
end if;
end if;
-- wraparound for ringbuffer case
if (r.HndlPtr1 = r.HndlWinEnd) and (r.HndlRingbuf = '1') then
v.HndlPtr2 := std_logic_vector(unsigned(r.HndlPtr1) - unsigned(r.HndlWinSize));
end if;
-- Update window information step 2 (limit to maximum value)
if unsigned(r.HndlWinBytes) > unsigned(r.HndlWinSize) then
v.HndlWinBytes := '0' & r.HndlWinSize; -- value has a guard bit
end if;
-- Store address of last sample in window
v.HndlWinLast := std_logic_vector(unsigned(r.HndlPtr1) - StreamWidth_g(r.HndlStream)/8);
-- Latch timestamp
if (Dma_Resp.Trigger = '1') and (Ts_Vld(r.HndlStream) = '1') then
v.Ts_Rdy(r.HndlStream) := '1';
v.HndlTs := Ts_Data(r.HndlStream);
else
v.HndlTs := (others => '1');
end if;
-- Write values
v.State := WriteCtx_s;
v.HndlCtxCnt := 0;
-- Response is processed
v.Dma_Resp_Rdy := '1';
-- Write Context Memory Content
when WriteCtx_s =>
-- Update State
if r.HndlCtxCnt = 2 then
v.State := Idle_s;
else
v.HndlCtxCnt := r.HndlCtxCnt + 1;
end if;
-- Write Context Memory
v.CtxStr_Cmd.Stream := v.HndlStream;
case r.HndlCtxCnt is
when 0 =>
-- Stream Memory
v.CtxStr_Cmd.Sel := CtxStr_Sel_ScfgBufstart_c;
v.CtxStr_Cmd.WenLo := '1';
v.CtxStr_Cmd.WdatLo(CtxStr_Sft_SCFG_RINGBUF_c) := r.HndlRingbuf;
v.CtxStr_Cmd.WdatLo(CtxStr_Sft_SCFG_OVERWRITE_c) := r.HndlOverwrite;
v.CtxStr_Cmd.WdatLo(CtxStr_Sft_SCFG_WINCNT_c+v.HndlWincnt'high downto CtxStr_Sft_SCFG_WINCNT_c) := r.HndlWincnt;
v.CtxStr_Cmd.WdatLo(CtxStr_Sft_SCFG_WINCUR_c+v.HndlWincur'high downto CtxStr_Sft_SCFG_WINCUR_c) := r.HndlWincur;
-- Window Memory
v.CtxWin_Cmd.Sel := CtxWin_Sel_WincntWinlast_c;
v.CtxWin_Cmd.WenLo := '1';
v.CtxWin_Cmd.WenHi := '1';
v.CtxWin_Cmd.WdatLo := ShiftRight(r.HndlWinBytes(31 downto 0), log2(StreamWidth_g(r.HndlStream)/8)); -- cut-off guard bit and convert bytes to samples
v.CtxWin_Cmd.WdatLo(31) := r.EndByTrig;
v.CtxWin_Cmd.WdatHi := r.HndlWinLast;
when 1 =>
-- Stream Memory
v.CtxStr_Cmd.Sel := CtxStr_Sel_WinsizePtr_c;
v.CtxStr_Cmd.WenHi := '1';
v.CtxStr_Cmd.WdatHi := r.HndlPtr2;
-- Window Memory
if r.HndlWinDone = '1' then
v.CtxWin_Cmd.Sel := CtxWin_Sel_WinTs_c;
v.CtxWin_Cmd.WenHi := '1';
v.CtxWin_Cmd.WenLo := '1';
v.CtxWin_Cmd.WdatLo := r.HndlTs(31 downto 0);
v.CtxWin_Cmd.WdatHi := r.HndlTs(63 downto 32);
end if;
when 2 =>
-- Stream Memory
v.CtxStr_Cmd.Sel := CtxStr_Sel_Winend_c;
v.CtxStr_Cmd.WenLo := '1';
v.CtxStr_Cmd.WdatLo := r.HndlWinEnd;
when others => null;
end case;
end case;
-- *** Handle Disabled Streams ***
for str in 0 to Streams_g-1 loop
if (r.GlbEnaReg = '0') or (r.StrEnaReg(str) = '0') then
v.FirstAfterEna(str) := '1';
v.NewBuffer(str) := '1';
end if;
end loop;
-- *** IRQ Handling ***
-- Feedback from memory controller
if r.TfDoneReg = '1' then
v.TfDoneCnt := std_logic_vector(unsigned(r.TfDoneCnt) + 1);
end if;
-- Process transfer completion
if (unsigned(r.TfDoneCnt) /= 0) and (IrqFifoEmpty = '0') then
v.IrqFifoRead := '1';
v.TfDoneCnt := std_logic_vector(unsigned(v.TfDoneCnt) - 1);
-- Generate IRQ if required
if IrqFifoGenIrq = '1' then
v.StrIrq(to_integer(unsigned(IrqFifoStream))) := '1';
end if;
end if;
-- *** Assign to signal ***
r_next <= v;
end process;
-- *** Registered Outputs ***
CtxStr_Cmd <= r.CtxStr_Cmd;
CtxWin_Cmd <= r.CtxWin_Cmd;
Dma_Cmd_Vld <= r.Dma_Cmd_Vld;
Dma_Cmd <= r.Dma_Cmd;
Dma_Resp_Rdy <= r.Dma_Resp_Rdy;
Ts_Rdy <= r.Ts_Rdy;
StrIrq <= r.StrIrq;
--------------------------------------------
-- Sequential Process
--------------------------------------------
p_seq : process(Clk)
begin
if rising_edge(Clk) then
r <= r_next;
if Rst = '1' then
r.ArbDelCnt <= 0;
r.InpDataAvail <= (others => '0');
r.DataAvailArbIn <= (others => '0');
r.HndlStream <= 0;
r.State <= Idle_s;
r.CtxStr_Cmd.WenLo <= '0';
r.CtxStr_Cmd.WenHi <= '0';
r.CtxWin_Cmd.WenLo <= '0';
r.CtxWin_Cmd.WenHi <= '0';
r.Dma_Cmd_Vld <= '0';
r.OpenCommand <= (others => '0');
r.WinProtected <= (others => '0');
r.Dma_Resp_Rdy <= '0';
r.Ts_Rdy <= (others => '0');
r.GlbEnaReg <= '0';
r.FirstOngoing <= (others => '0');
r.TfDoneCnt <= (others => '0');
r.TfDoneReg <= '0';
r.IrqFifoWrite <= '0';
r.IrqFifoRead <= '0';
r.StrIrq <= (others => '0');
end if;
end if;
end process;
--------------------------------------------
-- Component Instantiation
--------------------------------------------
-- *** Round Robin Arbiter - Prio 1 ***
AvailPrio1 <= GetBitsOfStreamPrio(r.DataAvailArbIn, 1);
i_rrarb_1 : entity work.psi_common_arb_priority
generic map (
Size_g => count(StreamPrio_g, 1)
)
port map (
Clk => Clk,
Rst => Rst,
Request => AvailPrio1,
Grant => GrantPrio1
);
GrantVld(1) <= '1' when (unsigned(GrantPrio1) /= 0) and (GrantPrio1'length > 0) else '0';
-- *** Round Robin Arbiter - Prio 2 ***
AvailPrio2 <= GetBitsOfStreamPrio(r.DataAvailArbIn, 2);
i_rrarb_2 : entity work.psi_common_arb_priority
generic map (
Size_g => count(StreamPrio_g, 2)
)
port map (
Clk => Clk,
Rst => Rst,
Request => AvailPrio2,
Grant => GrantPrio2
);
GrantVld(2) <= '1' when (unsigned(GrantPrio2) /= 0) and (GrantPrio2'length > 0) else '0';
-- *** Round Robin Arbiter - Prio 3 ***
AvailPrio3 <= GetBitsOfStreamPrio(r.DataAvailArbIn, 3);
i_rrarb_3 : entity work.psi_common_arb_priority
generic map (
Size_g => count(StreamPrio_g, 3)
)
port map (
Clk => Clk,
Rst => Rst,
Request => AvailPrio3,
Grant => GrantPrio3
);
GrantVld(3) <= '1' when (unsigned(GrantPrio3) /= 0) and (GrantPrio3'length > 0) else '0';
-- *** IRQ Information FIFO ***
-- input assembly
IrqFifoIn(IrqFifoIn'high-1 downto 0) <= std_logic_vector(to_unsigned(r.HndlStream, log2ceil(Streams_g)));
IrqFifoIn(IrqFifoIn'high) <= r.HndlWinDone;
-- Instantiation
i_irq_fifo : entity work.psi_common_sync_fifo
generic map (
Width_g => log2ceil(Streams_g)+1,
Depth_g => Streams_g*4,
AlmFullOn_g => true,
AlmFullLevel_g => Streams_g*3,
RamStyle_g => "distributed"
)
port map (
Clk => Clk,
Rst => Rst,
InData => IrqFifoIn,
InVld => r.IrqFifoWrite,
OutData => IrqFifoOut,
OutRdy => r.IrqFifoRead,
AlmFull => IrqFifoAlmFull,
Empty => IrqFifoEmpty
);
-- Output disassembly
IrqFifoStream <= IrqFifoOut(IrqFifoOut'high-1 downto 0);
IrqFifoGenIrq <= IrqFifoOut(IrqFifoOut'high);
end;

View File

@@ -1,541 +0,0 @@
------------------------------------------------------------------------------
-- Description
------------------------------------------------------------------------------
-- This component calculates a binary division of two fixed point values.
------------------------------------------------------------------------------
-- Libraries
------------------------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_ms_daq_pkg.all;
------------------------------------------------------------------------------
-- Entity Declaration
------------------------------------------------------------------------------
-- $$ testcases=single_frame,multi_frame,timeout,ts_overflow,trig_in_posttrig,always_trig,backpressure,modes $$
-- $$ processes=stream,daq $$
-- $$ tbpkg=work.psi_tb_txt_util $$
entity psi_ms_daq_input is
generic (
StreamWidth_g : positive range 8 to 64 := 16; -- Must be 8, 16, 32 or 64 $$ export=true $$
StreamBuffer_g : positive range 1 to 65535 := 1024; -- Buffer depth in QWORDs $$ constant=32 $$
StreamTimeout_g : real := 1.0e-3; -- Timeout in seconds $$ constant=10.0e-6 $$
StreamClkFreq_g : real := 125.0e6; -- Input clock frequency in Hz $$ constant=125.0e6 $$
StreamTsFifoDepth_g : positive := 16; -- Timestamp FIFO depth $$ constant=3 $$
StreamUseTs_g : boolean := true -- Enable/Disable the timestamp acquisition $$ constant=true $$
);
port (
-- Data Stream Input
Str_Clk : in std_logic; -- $$ type=clk; freq=125e6; proc=stream $$
Str_Vld : in std_logic; -- $$ proc=stream $$
Str_Rdy : out std_logic; -- $$ proc=stream $$
Str_Data : in std_logic_vector(StreamWidth_g-1 downto 0); -- $$ proc=stream $$
Str_Trig : in std_logic; -- $$ proc=stream $$
Str_Ts : in std_logic_vector(63 downto 0); -- $$ proc=stream $$
-- Configuration Signals
ClkTmem : in std_logic;
RstTmem : in std_logic;
PostTrigSpls : in std_logic_vector(31 downto 0); -- $$ proc=daq $$
Mode : in RecMode_t; -- $$ proc=daq $$
Arm : in std_logic; -- $$ proc=stream $$
IsArmed : out std_logic; -- $$ proc=stream $$
IsRecording : out std_logic; -- $$ proc=stream $$
-- DAQ control signals
ClkSmem : in std_logic; -- $$ type=clk; freq=200e6; proc=daq,stream $$
RstSmem : in std_logic; -- $$ type=rst; clk=Clk $$
-- DAQ logic Connections
Daq_Vld : out std_logic; -- $$ proc=daq $$
Daq_Rdy : in std_logic; -- $$ proc=daq $$
Daq_Data : out Input2Daq_Data_t; -- $$ proc=daq $$
Daq_Level : out std_logic_vector(15 downto 0); -- $$ proc=daq $$
Daq_HasLast : out std_logic; -- $$ proc=daq $$
-- Timestamp connections
Ts_Vld : out std_logic; -- $$ proc=daq $$
Ts_Rdy : in std_logic; -- $$ proc=daq $$
Ts_Data : out std_logic_vector(63 downto 0) -- $$ proc=daq $$
);
end entity;
------------------------------------------------------------------------------
-- Architecture Declaration
------------------------------------------------------------------------------
architecture rtl of psi_ms_daq_input is
-- Use distributed RAM for small Timstamp FIFOs (< 64 entries)
constant TsFifoStyle_c : string := choose(StreamTsFifoDepth_g <= 64, "distributed", "block");
-- Constants
constant TimeoutLimit_c : integer := integer(StreamClkFreq_g*StreamTimeout_g)-1;
constant WconvFactor_c : positive := 64/StreamWidth_g;
constant TlastCntWidth_c : positive := log2ceil(StreamBuffer_g) + 1;
-- Two process method
type two_process_r is record
ModeReg : RecMode_t;
ArmReg : std_logic;
DataSftReg : std_logic_vector(63 downto 0);
WordCnt : unsigned(log2ceil(WconvFactor_c) downto 0);
DataFifoBytes : unsigned(3 downto 0);
TrigLatch : std_logic;
DataFifoVld : std_logic;
DataFifoIsTo : std_logic;
DataFifoIsTrig : std_logic;
TimeoutCnt : integer range 0 to TimeoutLimit_c;
Timeout : std_logic;
PostTrigCnt : unsigned(31 downto 0);
TLastCnt : std_logic_vector(TlastCntWidth_c-1 downto 0);
TsLatch : std_logic_vector(63 downto 0);
TsOverflow : std_logic;
HasTlastSync : std_logic_vector(0 to 1);
IsArmed : std_logic;
RecEna : std_logic;
end record;
signal r, r_next : two_process_r;
-- General Instantiation signals
signal Str_Rst : std_logic;
-- Data FIFO signals
signal DataFifo_InRdy : std_logic;
signal DataFifo_InData : std_logic_vector(69 downto 0);
signal DataFifo_OutData : std_logic_vector(69 downto 0);
-- Internally reused signals
signal Daq_Data_I : Input2Daq_Data_t;
signal Daq_Vld_I : std_logic;
signal Daq_HasLast_I : std_logic;
signal Ts_Vld_I : std_logic;
-- Signal output side TLAST handling
signal OutTlastCnt : std_logic_vector(TlastCntWidth_c-1 downto 0);
signal InTlastCnt : std_logic_vector(TlastCntWidth_c-1 downto 0);
-- Timestamp FIFO signals
signal TsFifo_InRdy : std_logic;
signal TsFifo_InVld : std_logic;
signal TsFifo_RdData : std_logic_vector(63 downto 0);
signal TsFifo_AlmFull : std_logic;
signal TsFifo_Empty : std_logic;
-- Clock Crossing Signals
signal PostTrigSpls_Sync : std_logic_vector(PostTrigSpls'range);
signal Mode_Sync : RecMode_t;
signal Arm_Sync : std_logic;
signal RstTmem_Sync : std_logic;
signal RstAcq_Sync : std_logic;
begin
--------------------------------------------
-- Combinatorial Process
--------------------------------------------
p_comb : process( r,
Str_Vld, Str_Data, Str_Trig, Str_Ts, PostTrigSpls_Sync, Daq_Rdy, Ts_Rdy, Mode_Sync, Arm_Sync,
DataFifo_InRdy, DataFifo_InData, DataFifo_OutData, Daq_Vld_I, Daq_Data_I, Daq_HasLast_I, Ts_Vld_I, OutTlastCnt, TsFifo_AlmFull, TsFifo_Empty,
InTlastCnt, TsFifo_InRdy, TsFifo_RdData)
variable v : two_process_r;
variable ProcessSample_v : boolean;
variable TriggerSample_v : boolean;
variable AddSamples_v : integer range 0 to 1;
variable TrigMasked_v : std_logic;
begin
-- *** Hold variables stable ***
v := r;
-- *** Simplification Variables ***
ProcessSample_v := (DataFifo_InRdy = '1') and (Str_Vld = '1');
-- *** Input Logic Stage ***
-- Default values
v.DataFifoIsTo := '0';
v.DataFifoIsTrig := '0';
v.ModeReg := Mode_Sync;
v.ArmReg := Arm_Sync;
-- Masking trigger according to recording mode
case r.ModeReg is
when RecMode_Continuous_c =>
TrigMasked_v := Str_Trig;
when RecMode_TriggerMask_c |
RecMode_SingleShot_c =>
TrigMasked_v := Str_Trig and r.IsArmed;
when RecMode_ManuelMode_c =>
TrigMasked_v := r.ArmReg;
when others => null;
end case;
-- Keep FifoVld high until data is written
v.DataFifoVld := r.DataFifoVld and not DataFifo_InRdy;
-- Trigger Latching
if ProcessSample_v then
v.TrigLatch := '0';
else
v.TrigLatch := r.TrigLatch or TrigMasked_v;
end if;
-- Detect timestamp FIFO overflows
if StreamUseTs_g then
v.HasTlastSync(0) := Daq_HasLast_I;
v.HasTlastSync(1) := r.HasTlastSync(0);
if (TsFifo_AlmFull = '1' ) and (r.DataFifoVld = '1') then
v.TsOverflow := '1';
elsif (r.HasTlastSync(1) = '0') and (TsFifo_Empty = '1' ) then
v.TsOverflow := '0';
end if;
end if;
-- Timestamp latching
if StreamUseTs_g then
if (TrigMasked_v = '1') and (unsigned(r.PostTrigCnt) = 0) then
if (TsFifo_AlmFull = '1') or (r.TsOverflow = '1') then
v.TsLatch := (others => '1');
else
v.TsLatch := Str_Ts;
end if;
end if;
end if;
-- Trigger handling and post trigger counter
if ProcessSample_v and r.RecEna = '1' then
if r.PostTrigCnt /= 0 then
v.PostTrigCnt := r.PostTrigCnt - 1;
if r.PostTrigCnt = 1 then
v.DataFifoIsTrig := '1';
v.DataFifoVld := r.DataFifoVld or r.RecEna;
v.RecEna := '0'; -- stop recording after frame
end if;
elsif (r.TrigLatch = '1') or (TrigMasked_v = '1') then
-- Handle incoming trigger sample
if unsigned(PostTrigSpls_Sync) = 0 then
v.DataFifoIsTrig := '1';
v.DataFifoVld := r.DataFifoVld or r.RecEna;
v.RecEna := '0'; -- stop recording after frame
else
v.PostTrigCnt := unsigned(PostTrigSpls_Sync);
end if;
end if;
end if;
-- Detect Timeout
if Str_Vld = '1' then
v.TimeoutCnt := 0;
else
if r.TimeoutCnt = TimeoutLimit_c then
v.TimeoutCnt := 0;
v.Timeout := '1';
else
v.TimeoutCnt := r.TimeoutCnt + 1;
end if;
end if;
-- TLast counter
if (r.DataFifoVld = '1') and ((r.DataFifoIsTo = '1') or (r.DataFifoIsTrig = '1')) then
v.TLastCnt := std_logic_vector(unsigned(r.TLastCnt) + 1);
end if;
-- Write because timeout occured (only if data is stuck in conversion)
if r.Timeout = '1' then
v.DataFifoVld := r.DataFifoVld or r.RecEna;
v.DataFifoIsTo := '1';
v.Timeout := '0'; -- reser timeout after data was flushed to the FIFO
end if;
-- Process input data
if ProcessSample_v and r.RecEna = '1' then
v.WordCnt := r.WordCnt + 1;
-- Write because 64-bits are ready
if r.WordCnt = WconvFactor_c-1 then
v.DataFifoVld := r.DataFifoVld or r.RecEna;
end if;
v.DataSftReg(to_integer(r.WordCnt+1)*StreamWidth_g-1 downto to_integer(r.WordCnt)*StreamWidth_g) := Str_Data;
end if;
-- Reset counter if data is being written to FIFO
if v.DataFifoVld = '1' then
v.WordCnt := (others => '0');
end if;
-- Convert word counter to byte counter
v.DataFifoBytes := (others => '0');
if r.Timeout = '1' then
AddSamples_v := 0;
else
AddSamples_v := 1;
end if;
case StreamWidth_g is
when 8 => v.DataFifoBytes := r.WordCnt + AddSamples_v;
when 16 => v.DataFifoBytes := (r.WordCnt + AddSamples_v) & "0";
when 32 => v.DataFifoBytes := (r.WordCnt + AddSamples_v) & "00";
when 64 => v.DataFifoBytes := (r.WordCnt + AddSamples_v) & "000";
when others => null;
end case;
-- Handle Arming Logic
if (r.ModeReg /= Mode_Sync) or (r.ModeReg = RecMode_Continuous_c) or (r.ModeReg = RecMode_ManuelMode_c) then -- reset on mode change!
v.IsArmed := '0';
elsif r.ArmReg = '1' then
v.IsArmed := '1';
elsif TrigMasked_v = '1' then
v.IsArmed := '0';
end if;
-- Enable Recording Logic
case r.ModeReg is
when RecMode_Continuous_c |
RecMode_TriggerMask_c =>
-- always enabled
v.RecEna := '1';
when RecMode_SingleShot_c |
RecMode_ManuelMode_c =>
-- enable on arming (disable happens after recording)
if v.ArmReg = '1' then
v.RecEna := '1';
end if;
when others => null;
end case;
if r.ModeReg /= Mode_Sync then
v.RecEna := '0';
end if;
-- *** Assign to signal ***
r_next <= v;
end process;
--------------------------------------------
-- Sequential Process
--------------------------------------------
p_seq : process(Str_Clk)
begin
if rising_edge(Str_Clk) then
r <= r_next;
if Str_Rst = '1' then
r.WordCnt <= (others => '0');
r.TrigLatch <= '0';
r.TimeoutCnt <= 0;
r.Timeout <= '0';
r.PostTrigCnt <= (others => '0');
r.TLastCnt <= (others => '0');
r.TsOverflow <= '0';
r.HasTlastSync <= (others => '0');
r.IsArmed <= '0';
r.RecEna <= '0';
r.ArmReg <= '0';
end if;
end if;
end process;
--------------------------------------------
-- Output Side TLAST handling
--------------------------------------------
p_outlast : process(ClkSmem)
begin
if rising_edge(ClkSmem) then
-- Default Value
Daq_HasLast_I <= '0';
-- Count TLAST read from output buffer
if (Daq_Vld_I = '1') and (Daq_Rdy = '1') and (Daq_Data_I.Last = '1') then
OutTlastCnt <= std_logic_vector(unsigned(OutTlastCnt) + 1);
end if;
-- Detect if there are TLASTs in the buffer
if OutTlastCnt /= InTlastCnt then
Daq_HasLast_I <= '1';
end if;
-- Reset
if RstSmem = '1' then
OutTlastCnt <= (others => '0');
end if;
end if;
end process;
Daq_HasLast <= Daq_HasLast_I;
--------------------------------------------
-- Component Instantiation
--------------------------------------------
-- *** TMEM clock crossings ***
i_cc_tmem_status : entity work.psi_common_status_cc
generic map (
DataWidth_g => 34
)
port map (
ClkA => ClkTmem,
RstInA => '0',
DataA(31 downto 0) => PostTrigSpls,
DataA(33 downto 32) => Mode,
ClkB => Str_Clk,
RstInB => Str_Rst,
DataB(31 downto 0) => PostTrigSpls_Sync,
DataB(33 downto 32) => Mode_Sync
);
i_cc_status : entity work.psi_common_bit_cc
generic map (
NumBits_g => 2
)
port map (
BitsA(0) => r.IsArmed,
BitsA(1) => r.RecEna,
ClkB => ClkTmem,
BitsB(0) => IsArmed,
BitsB(1) => IsRecording
);
i_cc_tmem_pulse : entity work.psi_common_pulse_cc
generic map (
NumPulses_g => 1
)
port map (
ClkA => ClkTmem,
RstInA => '0',
PulseA(0) => Arm,
ClkB => Str_Clk,
RstInB => Str_Rst,
RstOutB => open,
PulseB(0) => Arm_Sync
);
-- *** Reset Handling ***
icc_tmem_rst : entity work.psi_common_bit_cc
generic map (
NumBits_g => 1
)
port map (
BitsA(0) => RstTmem,
ClkB => Str_Clk,
BitsB(0) => RstTmem_Sync
);
icc_smem_rst : entity work.psi_common_bit_cc
generic map (
NumBits_g => 1
)
port map (
BitsA(0) => RstSmem,
ClkB => Str_Clk,
BitsB(0) => RstAcq_Sync
);
Str_Rst <= RstTmem_Sync or RstAcq_Sync;
-- *** Acquisition Clock Crossing ***
-- Clock crossing for reset and TLAST counter
i_cc : entity work.psi_common_status_cc
generic map (
DataWidth_g => TlastCntWidth_c
)
port map (
ClkA => Str_Clk,
RstInA => Str_Rst,
RstOutA => open,
DataA => r.TLastCnt,
ClkB => ClkSmem,
RstInB => '0',
DataB => InTlastCnt
);
-- Data FIFO
DataFifo_InData(63 downto 0) <= r.DataSftReg;
DataFifo_InData(67 downto 64) <= std_logic_vector(r.DataFifoBytes);
DataFifo_InData(68) <= r.DataFifoIsTo;
DataFifo_InData(69) <= r.DataFifoIsTrig;
i_dfifo : entity work.psi_common_async_fifo
generic map (
Width_g => 70,
Depth_g => StreamBuffer_g,
AlmFullOn_g => false,
AlmEmptyOn_g => false
)
port map (
InClk => Str_Clk,
InRst => Str_Rst,
OutClk => ClkSmem,
OutRst => '0',
InData => DataFifo_InData,
InVld => r.DataFifoVld,
InRdy => DataFifo_InRdy,
OutData => DataFifo_OutData,
OutVld => Daq_Vld_I,
OutRdy => Daq_Rdy,
OutLevel => Daq_Level(log2ceil(StreamBuffer_g) downto 0)
);
Daq_Level(Daq_Level'high downto log2ceil(StreamBuffer_g)+1) <= (others => '0');
Str_Rdy <= DataFifo_InRdy;
Daq_Data_I.Data <= DataFifo_OutData(63 downto 0);
Daq_Data_I.Bytes <= DataFifo_OutData(67 downto 64);
Daq_Data_I.IsTo <= DataFifo_OutData(68);
Daq_Data_I.IsTrig <= DataFifo_OutData(69);
Daq_Data_I.Last <= Daq_Data_I.IsTo or Daq_Data_I.IsTrig;
Daq_Data <= Daq_Data_I;
Daq_Vld <= Daq_Vld_I;
-- Timestamp FIFO
g_timestamp : if StreamUseTs_g generate
TsFifo_InVld <= r.DataFifoVld and r.DataFifoIsTrig;
i_tsfifo : entity work.psi_common_async_fifo
generic map (
Width_g => 64,
Depth_g => StreamTsFifoDepth_g,
AlmFullOn_g => True,
AlmFullLevel_g => StreamTsFifoDepth_g-1,
AlmEmptyOn_g => false,
RamStyle_g => TsFifoStyle_c
)
port map (
InClk => Str_Clk,
InRst => Str_Rst,
OutClk => ClkSmem,
OutRst => '0',
InData => r.TsLatch,
InVld => TsFifo_InVld,
InRdy => TsFifo_InRdy,
InAlmFull => TsFifo_AlmFull,
InEmpty => TsFifo_Empty,
OutData => TsFifo_RdData,
OutVld => Ts_Vld_I,
OutRdy => Ts_Rdy
);
Ts_Vld <= Ts_Vld_I;
-- Replace data by 0xFF... if no valid timestamp is available
Ts_Data <= (others => '1') when Ts_Vld_I = '0' else TsFifo_RdData;
end generate;
g_ntimestamp : if not StreamUseTs_g generate
Ts_Vld <= '0';
Ts_Data <= (others => '1');
end generate;
--------------------------------------------
-- Assertions
--------------------------------------------
p_assert : process(ClkSmem)
begin
if rising_edge(ClkSmem) then
assert StreamWidth_g = 8 or StreamWidth_g = 16 or StreamWidth_g = 32 or StreamWidth_g = 64 report "###ERROR###: psi_ms_daq_input: StreamWidth_g must be 8, 16, 32 or 64" severity error;
end if;
end process;
end;

View File

@@ -1,153 +0,0 @@
------------------------------------------------------------------------------
-- Libraries
------------------------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
------------------------------------------------------------------------------
-- Package Header
------------------------------------------------------------------------------
package psi_ms_daq_pkg is
constant MaxStreams_c : integer := 32;
constant MaxWindows_c : integer := 32;
constant MaxStreamsBits_c : integer := log2ceil(MaxStreams_c);
subtype RecMode_t is std_logic_vector(1 downto 0);
constant RecMode_Continuous_c : RecMode_t := std_logic_vector(to_unsigned(0, RecMode_t'length));
constant RecMode_TriggerMask_c : RecMode_t := std_logic_vector(to_unsigned(1, RecMode_t'length));
constant RecMode_SingleShot_c : RecMode_t := std_logic_vector(to_unsigned(2, RecMode_t'length));
constant RecMode_ManuelMode_c : RecMode_t := std_logic_vector(to_unsigned(3, RecMode_t'length));
type Input2Daq_Data_t is record
Last : std_logic;
Data : std_logic_vector(63 downto 0);
Bytes : std_logic_vector(3 downto 0);
IsTo : std_logic;
IsTrig : std_logic;
end record;
type Input2Daq_Data_a is array (natural range <>) of Input2Daq_Data_t;
type DaqSm2DaqDma_Cmd_t is record
Address : std_logic_vector(31 downto 0);
MaxSize : std_logic_vector(15 downto 0);
Stream : integer range 0 to MaxStreams_c-1;
end record;
constant DaqSm2DaqDma_Cmd_Size_c : integer := 32+16+MaxStreamsBits_c;
function DaqSm2DaqDma_Cmd_ToStdlv( rec : DaqSm2DaqDma_Cmd_t) return std_logic_vector;
function DaqSm2DaqDma_Cmd_FromStdlv( stdlv : std_logic_vector) return DaqSm2DaqDma_Cmd_t;
type DaqDma2DaqSm_Resp_t is record
Size : std_logic_vector(15 downto 0);
Trigger : std_logic;
Stream : integer range 0 to MaxStreams_c-1;
end record;
constant DaqDma2DaqSm_Resp_Size_c : integer := 16+1+MaxStreamsBits_c;
function DaqDma2DaqSm_Resp_ToStdlv( rec : DaqDma2DaqSm_Resp_t) return std_logic_vector;
function DaqDme2DaqSm_Resp_FromStdlv( stdlv : std_logic_vector) return DaqDma2DaqSm_Resp_t;
type ToCtxStr_t is record
Stream : integer range 0 to MaxStreams_c-1;
Sel : std_logic_vector(1 downto 0);
Rd : std_logic;
WenLo : std_logic;
WenHi : std_logic;
WdatLo : std_logic_vector(31 downto 0);
WdatHi : std_logic_vector(31 downto 0);
end record;
constant CtxStr_Sel_ScfgBufstart_c : std_logic_vector(1 downto 0) := "00";
constant CtxStr_Sel_WinsizePtr_c : std_logic_vector(1 downto 0) := "01";
constant CtxStr_Sel_Winend_c : std_logic_vector(1 downto 0) := "10";
constant CtxStr_Sft_SCFG_RINGBUF_c : integer := 0;
constant CtxStr_Sft_SCFG_OVERWRITE_c : integer := 8;
constant CtxStr_Sft_SCFG_WINCNT_c : integer := 16;
constant CtxStr_Sft_SCFG_WINCUR_c : integer := 24;
type ToCtxWin_t is record
Stream : integer range 0 to MaxStreams_c-1;
Window : integer range 0 to MaxWindows_c-1;
Sel : std_logic_vector(0 downto 0);
Rd : std_logic;
WenLo : std_logic;
WenHi : std_logic;
WdatLo : std_logic_vector(31 downto 0);
WdatHi : std_logic_vector(31 downto 0);
end record;
constant CtxWin_Sel_WincntWinlast_c : std_logic_vector(0 downto 0) := "0";
constant CtxWin_Sel_WinTs_c : std_logic_vector(0 downto 0) := "1";
type FromCtx_t is record
RdatLo : std_logic_vector(31 downto 0);
RdatHi : std_logic_vector(31 downto 0);
end record;
type TmemRqst_t is record
ADD : std_logic_vector(23 downto 0);
DATW : std_logic_vector(63 downto 0);
ENA : std_logic;
WE : std_logic_vector(7 downto 0);
CS : std_logic_vector(1 downto 0);
end record;
constant TmemRqst_init_c : TmemRqst_t := ((others => '0'), (others => '0'), '0', (others => '0'), (others => '0'));
type TmemResp_t is record
DATR : std_logic_vector(63 downto 0);
BUSY : std_logic;
PIPE : std_logic_vector(1 downto 0);
end record;
end psi_ms_daq_pkg;
------------------------------------------------------------------------------
-- Package Body
------------------------------------------------------------------------------
package body psi_ms_daq_pkg is
-- *** DaqSm2DaqDma_Cmd ***
function DaqSm2DaqDma_Cmd_ToStdlv( rec : DaqSm2DaqDma_Cmd_t) return std_logic_vector is
variable stdlv : std_logic_vector(DaqSm2DaqDma_Cmd_Size_c-1 downto 0);
begin
stdlv(31 downto 0) := rec.Address;
stdlv(47 downto 32) := rec.MaxSize;
stdlv(stdlv'left downto 48) := std_logic_vector(to_unsigned(rec.Stream, MaxStreamsBits_c));
return stdlv;
end function;
function DaqSm2DaqDma_Cmd_FromStdlv( stdlv : std_logic_vector) return DaqSm2DaqDma_Cmd_t is
variable rec : DaqSm2DaqDma_Cmd_t;
begin
rec.Address := stdlv(31 downto 0);
rec.MaxSize := stdlv(47 downto 32);
rec.Stream := to_integer(unsigned(stdlv(stdlv'left downto 48)));
return rec;
end function;
-- *** DaqDma2DaqSm_Resp ***
function DaqDma2DaqSm_Resp_ToStdlv( rec : DaqDma2DaqSm_Resp_t) return std_logic_vector is
variable stdlv : std_logic_vector(DaqDma2DaqSm_Resp_Size_c-1 downto 0);
begin
stdlv(15 downto 0) := rec.Size;
stdlv(16) := rec.Trigger;
stdlv(stdlv'left downto 17) := std_logic_vector(to_unsigned(rec.Stream, MaxStreamsBits_c));
return stdlv;
end function;
function DaqDme2DaqSm_Resp_FromStdlv( stdlv : std_logic_vector) return DaqDma2DaqSm_Resp_t is
variable rec : DaqDma2DaqSm_Resp_t;
begin
rec.Size := stdlv(15 downto 0);
rec.Trigger := stdlv(16);
rec.Stream := to_integer(unsigned(stdlv(stdlv'left downto 17)));
return rec;
end function;
end psi_ms_daq_pkg;

View File

@@ -1,425 +0,0 @@
------------------------------------------------------------------------------
-- Libraries
------------------------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_common_array_pkg.all;
use work.psi_common_logic_pkg.all;
use work.psi_ms_daq_pkg.all;
------------------------------------------------------------------------------
-- Entity Declaration
------------------------------------------------------------------------------
entity psi_ms_daq_reg_tmem is
generic (
Streams_g : in integer range 1 to 32;
MaxWindows_g : in integer range 1 to 32
);
port (
-- TMEM Interface
ClkTmem : in std_logic;
RstTmem : in std_logic;
TmemRqst : in TmemRqst_t;
TmemResp : out TmemResp_t;
-- Control Signals (TMEM Clk)
Arm : out std_logic_vector(Streams_g-1 downto 0);
IsArmed : in std_logic_vector(Streams_g-1 downto 0);
IsRecording : in std_logic_vector(Streams_g-1 downto 0);
PostTrig : out t_aslv32(Streams_g-1 downto 0);
RecMode : out t_aslv2(Streams_g-1 downto 0);
IrqOut : out std_logic;
-- SMEM Clock domain control singals
ClkSmem : in std_logic;
RstSmem : in std_logic;
-- Context Memory Interface (SMEM Clk)
CtxStr_Cmd : in ToCtxStr_t;
CtxStr_Resp : out FromCtx_t;
CtxWin_Cmd : in ToCtxWin_t;
CtxWin_Resp : out FromCtx_t;
-- Logic Interface (SMEM Clk)
StrIrq : in std_logic_vector(Streams_g-1 downto 0);
StrEna : out std_logic_vector(Streams_g-1 downto 0);
GlbEna : out std_logic;
InLevel : in t_aslv16(Streams_g-1 downto 0)
);
end entity;
architecture rtl of psi_ms_daq_reg_tmem is
-- Two process method
type two_process_r is record
Reg_Gcfg_Ena : std_logic;
Reg_Gcfg_IrqEna : std_logic;
Reg_IrqVec : std_logic_vector(Streams_g-1 downto 0);
Reg_IrqEna : std_logic_vector(Streams_g-1 downto 0);
Reg_StrEna : std_logic_vector(Streams_g-1 downto 0);
Reg_PostTrig : t_aslv32(Streams_g-1 downto 0);
Reg_Mode_Recm : t_aslv2(Streams_g-1 downto 0);
Reg_Mode_Arm : std_logic_vector(Streams_g-1 downto 0);
Irq : std_logic;
RegRdval : std_logic_vector(63 downto 0);
RdVal : std_logic_vector(63 downto 0);
AddrReg : std_logic_vector(23 downto 0);
MaxLvlClr : std_logic_vector(Streams_g-1 downto 0);
end record;
signal r, r_next : two_process_r;
constant DwWrite_c : std_logic_vector(3 downto 0) := "1111";
subtype WeHigh_c is natural range 7 downto 4;
subtype WeLow_c is natural range 3 downto 0;
constant DepthCtxStr_c : integer := Streams_g*32/8;
constant CtxStrAddrHigh_c : integer := log2ceil(Streams_g*32)-1;
signal CtxStr_WeLo : std_logic;
signal CtxStr_WeHi : std_logic;
signal CtxStr_Rdval : std_logic_vector(63 downto 0);
signal CtxStr_AddrB : std_logic_vector(log2ceil(DepthCtxStr_c)-1 downto 0);
signal AddrCtxStr : boolean;
constant DepthCtxWin_c : integer := Streams_g*MaxWindows_g*16/8;
constant CtxWinAddrHigh_c : integer := log2ceil(Streams_g*MaxWindows_g*16)-1;
signal CtxWin_WeLo : std_logic;
signal CtxWin_WeHi : std_logic;
signal CtxWin_Rdval : std_logic_vector(63 downto 0);
signal CtxWin_AddrB : std_logic_vector(log2ceil(DepthCtxWin_c)-1 downto 0);
signal AddrCtxWin : boolean;
-- Maximum Level Latching
signal MaxLevel : t_aslv16(Streams_g-1 downto 0);
-- Clock Crossing Signals
signal StrIrq_Sync : std_logic_vector(Streams_g-1 downto 0);
signal MaxLevel_Sync : t_aslv16(Streams_g-1 downto 0);
signal MaxLevelClr_Sync : std_logic_vector(Streams_g-1 downto 0);
begin
--------------------------------------------
-- Combinatorial Process
--------------------------------------------
p_comb : process( r, TmemRqst, StrIrq_Sync, IsArmed, IsRecording, CtxStr_Rdval, CtxWin_Rdval, MaxLevel)
variable v : two_process_r;
variable Stream_v : integer range 0 to Streams_g-1;
begin
-- *** Hold variables stable ***
v := r;
-- *** General Register Accesses ***
v.RegRdval := (others => '0');
if TmemRqst.ENA = '1' then
case TmemRqst.ADD is
-- GCFG / GSTAT
when X"000000" =>
-- GCFG
if TmemRqst.WE(0) = '1' then
v.Reg_Gcfg_Ena := TmemRqst.DATW(0);
end if;
if TmemRqst.WE(1) = '1' then
v.Reg_Gcfg_IrqEna := TmemRqst.DATW(8);
end if;
v.RegRdval(0) := r.Reg_Gcfg_Ena;
v.RegRdval(8) := r.Reg_Gcfg_IrqEna;
-- IRQVEC / IRQENA
when X"000010" =>
-- IRQVEC
if TmemRqst.WE(WeLow_c) = DwWrite_c then
v.Reg_IrqVec := r.Reg_IrqVec and (not TmemRqst.DATW(Streams_g-1 downto 0));
end if;
v.RegRdval(Streams_g-1 downto 0) := r.Reg_IrqVec;
-- IRQENA
if TmemRqst.WE(WeHigh_c) = DwWrite_c then
v.Reg_IrqEna := TmemRqst.DATW(Streams_g+32-1 downto 32);
end if;
v.RegRdval(Streams_g+32-1 downto 32) := r.Reg_IrqEna;
-- STRENA
when X"000020" =>
-- STRENA
if TmemRqst.WE(WeLow_c) = DwWrite_c then
v.Reg_StrEna := TmemRqst.DATW(Streams_g-1 downto 0);
end if;
v.RegRdval(Streams_g-1 downto 0) := r.Reg_StrEna;
-- others clause
when others => null;
end case;
end if;
-- *** Stream Register Accesses ***
v.Reg_Mode_Arm := (others => '0');
v.MaxLvlClr := (others => '0');
if TmemRqst.ENA = '1' then
if TmemRqst.ADD(23 downto 9) = X"000" & "001" then
Stream_v := to_integer(unsigned(TmemRqst.ADD(8 downto 4)));
-- MAXLVLn / POSTTRIGn
if TmemRqst.ADD(3 downto 0) = X"0" then
-- MAXLVLn
if TmemRqst.WE(WeLow_c) = DwWrite_c then
v.MaxLvlClr(Stream_v) := '1';
end if;
v.RegRdval(15 downto 0) := MaxLevel(Stream_v);
-- POSTTRIGn
if TmemRqst.WE(WeHigh_c) = DwWrite_c then
v.Reg_PostTrig(Stream_v) := TmemRqst.DATW(63 downto 32);
end if;
v.RegRdval(63 downto 32) := r.Reg_PostTrig(Stream_v);
end if;
-- MODEn
if TmemRqst.ADD(3 downto 0) = X"8" then
-- MODEn
if TmemRqst.WE(0) = '1' then
v.Reg_Mode_Recm(Stream_v) := TmemRqst.DATW(1 downto 0);
end if;
if TmemRqst.WE(1) = '1' then
v.Reg_Mode_Arm(Stream_v) := TmemRqst.DATW(8);
end if;
v.RegRdval(1 downto 0) := r.Reg_Mode_Recm(Stream_v);
v.RegRdval(8) := IsArmed(Stream_v);
v.RegRdval(16) := IsRecording(Stream_v);
end if;
end if;
end if;
-- *** Read Data MUX ***
v.AddrReg := TmemRqst.ADD;
v.RdVal := (others => '0');
if r.AddrReg(23 downto 12) = X"000" then
v.RdVal := r.RegRdval;
elsif r.AddrReg(23 downto 12) = X"001" then
v.RdVal := CtxStr_Rdval;
elsif r.AddrReg(23 downto 14) = X"00" & "01" then
v.RdVal := CtxWin_Rdval;
end if;
-- *** IRQ Handling ***
for i in 0 to Streams_g-1 loop
if (StrIrq_Sync(i) = '1') and (r.Reg_StrEna(i) = '1') then
v.Reg_IrqVec(i) := '1';
end if;
end loop;
if ((r.Reg_IrqVec and r.Reg_IrqEna) /= ZerosVector(Streams_g)) and (r.Reg_Gcfg_IrqEna = '1') then
v.Irq := '1';
else
v.Irq := '0';
end if;
-- *** Assign to signal ***
r_next <= v;
end process;
-- *** Registered Outputs ***
TmemResp.PIPE <= "10";
TmemResp.BUSY <= '0';
TmemResp.DATR <= r.RdVal;
IrqOut <= r.Irq;
PostTrig <= r.Reg_PostTrig;
Arm <= r.Reg_Mode_Arm;
RecMode <= r.Reg_Mode_Recm;
--------------------------------------------
-- Sequential Process
--------------------------------------------
p_seq : process(ClkTmem)
begin
if rising_edge(ClkTmem) then
r <= r_next;
if RstTmem = '1' then
r.Reg_Gcfg_Ena <= '0';
r.Reg_Gcfg_IrqEna <= '0';
r.Reg_IrqVec <= (others => '0');
r.Reg_IrqEna <= (others => '0');
r.Reg_StrEna <= (others => '0');
r.Irq <= '0';
r.Reg_PostTrig <= (others => (others => '0'));
r.Reg_Mode_Recm <= (others => (others => '0'));
r.Reg_Mode_Arm <= (others => '0');
end if;
end if;
end process;
--------------------------------------------
-- Maximum Level Latching (SmemClk)
--------------------------------------------
p_maxlvl : process(ClkSmem)
begin
if rising_edge(ClkSmem) then
if RstSmem = '1' then
MaxLevel <= (others => (others => '0'));
else
-- Latch maximum level
for i in 0 to Streams_g-1 loop
if MaxLevelClr_Sync(i) = '1' then
MaxLevel(i) <= (others => '0');
elsif unsigned(InLevel(i)) > unsigned(MaxLevel(i)) then
MaxLevel(i) <= InLevel(i);
end if;
end loop;
end if;
end if;
end process;
--------------------------------------------
-- Component Instantiations
--------------------------------------------
-- *** Clock Crossings ***
i_cc_smem_in : entity work.psi_common_pulse_cc
generic map (
NumPulses_g => Streams_g
)
port map (
ClkA => ClkSmem,
RstInA => RstSmem,
PulseA => StrIrq,
ClkB => ClkTmem,
RstInB => RstTmem,
PulseB => StrIrq_Sync
);
blk_cc_smem_out : block
signal ccIn, ccOut : std_logic_vector(Streams_g downto 0);
begin
-- Input Assembly
ccIn(Streams_g-1 downto 0) <= r.Reg_StrEna;
ccIn(Streams_g) <= r.Reg_Gcfg_Ena;
-- Instantiation
i_cc_smem_out : entity work.psi_common_bit_cc
generic map (
NumBits_g => Streams_g+1
)
port map (
BitsA => ccIn,
ClkB => ClkSmem,
BitsB => ccOut
);
-- Output assembly
StrEna <= ccOut(Streams_g-1 downto 0);
GlbEna <= ccOut(Streams_g);
end block;
i_cc_smem_out_pulse : entity work.psi_common_pulse_cc
generic map (
NumPulses_g => Streams_g
)
port map (
ClkA => ClkTmem,
RstInA => RstTmem,
PulseA => r.MaxLvlClr,
ClkB => ClkSmem,
RstInB => RstSmem,
PulseB => MaxLevelClr_Sync
);
-- *** Stream Context Memory ***
-- Signal Assembly
AddrCtxStr <= TmemRqst.ADD(23 downto 12) = X"001";
CtxStr_WeLo <= '1' when TmemRqst.WE(WeLow_c) = DwWrite_c and AddrCtxStr and TmemRqst.ENA = '1' else '0';
CtxStr_WeHi <= '1' when TmemRqst.WE(WeHigh_c) = DwWrite_c and AddrCtxStr and TmemRqst.ENA = '1' else '0';
CtxStr_AddrB <= std_logic_vector(to_unsigned(CtxStr_Cmd.Stream, log2ceil(Streams_g))) & CtxStr_Cmd.Sel;
-- Low DWORD memory
i_mem_ctx_lo : entity work.psi_common_tdp_ram
generic map (
Depth_g => DepthCtxStr_c,
Width_g => 32,
Behavior_g => "RBW"
)
port map (
ClkA => ClkTmem,
AddrA => TmemRqst.ADD(CtxStrAddrHigh_c downto 3),
WrA => CtxStr_WeLo,
DinA => TmemRqst.DATW(31 downto 0),
DoutA => CtxStr_Rdval(31 downto 0),
ClkB => ClkSmem,
AddrB => CtxStr_AddrB,
WrB => CtxStr_Cmd.WenLo,
DinB => CtxStr_Cmd.WdatLo,
DoutB => CtxStr_Resp.RdatLo
);
-- High DWORD memory
i_mem_ctx_hi : entity work.psi_common_tdp_ram
generic map (
Depth_g => DepthCtxStr_c,
Width_g => 32,
Behavior_g => "RBW"
)
port map (
ClkA => ClkTmem,
AddrA => TmemRqst.ADD(CtxStrAddrHigh_c downto 3),
WrA => CtxStr_WeHi,
DinA => TmemRqst.DATW(63 downto 32),
DoutA => CtxStr_Rdval(63 downto 32),
ClkB => ClkSmem,
AddrB => CtxStr_AddrB,
WrB => CtxStr_Cmd.WenHi,
DinB => CtxStr_Cmd.WdatHi,
DoutB => CtxStr_Resp.RdatHi
);
-- *** Window Context Memory ***
-- Signal Assembly
AddrCtxWin <= TmemRqst.ADD(23 downto 14) = X"00" & "01";
CtxWin_WeLo <= '1' when TmemRqst.WE(WeLow_c) = DwWrite_c and AddrCtxWin and TmemRqst.ENA = '1' else '0';
CtxWin_WeHi <= '1' when TmemRqst.WE(WeHigh_c) = DwWrite_c and AddrCtxWin and TmemRqst.ENA = '1'else '0';
CtxWin_AddrB <= std_logic_vector(to_unsigned(CtxWin_Cmd.Stream, log2ceil(Streams_g))) &
std_logic_vector(to_unsigned(CtxWin_Cmd.Window, log2ceil(MaxWindows_g))) &
CtxWin_Cmd.Sel;
-- Low DWORD memory
i_mem_win_lo : entity work.psi_common_tdp_ram
generic map (
Depth_g => DepthCtxWin_c,
Width_g => 32,
Behavior_g => "RBW"
)
port map (
ClkA => ClkTmem,
AddrA => TmemRqst.ADD(CtxWinAddrHigh_c downto 3),
WrA => CtxWin_WeLo,
DinA => TmemRqst.DATW(31 downto 0),
DoutA => CtxWin_Rdval(31 downto 0),
ClkB => ClkSmem,
AddrB => CtxWin_AddrB,
WrB => CtxWin_Cmd.WenLo,
DinB => CtxWin_Cmd.WdatLo,
DoutB => CtxWin_Resp.RdatLo
);
-- High DWORD memory
i_mem_win_hi : entity work.psi_common_tdp_ram
generic map (
Depth_g => DepthCtxWin_c,
Width_g => 32,
Behavior_g => "RBW"
)
port map (
ClkA => ClkTmem,
AddrA => TmemRqst.ADD(CtxWinAddrHigh_c downto 3),
WrA => CtxWin_WeHi,
DinA => TmemRqst.DATW(63 downto 32),
DoutA => CtxWin_Rdval(63 downto 32),
ClkB => ClkSmem,
AddrB => CtxWin_AddrB,
WrB => CtxWin_Cmd.WenHi,
DinB => CtxWin_Cmd.WdatHi,
DoutB => CtxWin_Resp.RdatHi
);
end architecture;

14
sim/.gitignore vendored
View File

@@ -1,14 +0,0 @@
#TCL controlled modelsim .Gitignore
#Ignore all library files
*/_info
*.qdb
*.qpg
*.qtl
*/_vmake
*/_*/**/*
*/@_opt/**/*
#Ignore transcripts
*.transcript
*.wlf

View File

@@ -1,110 +0,0 @@
#Constants
set LibPath "../../../VHDL"
#Import psi::sim
namespace import psi::sim::*
#Set library
add_library psi_ms_daq
#suppress messages
compile_suppress 135,1236,1073,1246
run_suppress 8684,3479,3813,8009,3812
# Library
add_sources $LibPath {
psi_tb/hdl/psi_tb_txt_util.vhd \
psi_tb/hdl/psi_tb_compare_pkg.vhd \
psi_tb/hdl/psi_tb_activity_pkg.vhd \
psi_common/hdl/psi_common_array_pkg.vhd \
psi_common/hdl/psi_common_math_pkg.vhd \
psi_common/hdl/psi_common_logic_pkg.vhd \
psi_common/hdl/psi_common_sdp_ram.vhd \
psi_common/hdl/psi_common_pulse_cc.vhd \
psi_common/hdl/psi_common_bit_cc.vhd \
psi_common/hdl/psi_common_simple_cc.vhd \
psi_common/hdl/psi_common_status_cc.vhd \
psi_common/hdl/psi_common_async_fifo.vhd \
psi_common/hdl/psi_common_arb_priority.vhd \
psi_common/hdl/psi_common_sync_fifo.vhd \
psi_common/hdl/psi_common_tdp_ram.vhd \
../../BoardSupport/IFC1210/smem_master/hdl/smem_master_types_pkg.vhd \
../../BoardSupport/IFC1210/smem_master/hdl/smem_master_write.vhd \
} -tag lib
# project sources
add_sources "../hdl" {
psi_ms_daq_pkg.vhd \
psi_ms_daq_input.vhd \
psi_ms_daq_daq_sm.vhd \
psi_ms_daq_daq_dma.vhd \
psi_ms_daq_reg_tmem.vhd \
psi_ms_daq.vhd \
} -tag src
# testbenches
add_sources "../tb" {
psi_ms_daq_input/psi_ms_daq_input_tb_pkg.vhd \
psi_ms_daq_input/psi_ms_daq_input_tb_case_single_frame.vhd \
psi_ms_daq_input/psi_ms_daq_input_tb_case_multi_frame.vhd \
psi_ms_daq_input/psi_ms_daq_input_tb_case_timeout.vhd \
psi_ms_daq_input/psi_ms_daq_input_tb_case_ts_overflow.vhd \
psi_ms_daq_input/psi_ms_daq_input_tb_case_trig_in_posttrig.vhd \
psi_ms_daq_input/psi_ms_daq_input_tb_case_backpressure.vhd \
psi_ms_daq_input/psi_ms_daq_input_tb_case_always_trig.vhd \
psi_ms_daq_input/psi_ms_daq_input_tb_case_modes.vhd \
psi_ms_daq_input/psi_ms_daq_input_tb.vhd \
psi_ms_daq_daq_sm/psi_ms_daq_daq_sm_tb_pkg.vhd \
psi_ms_daq_daq_sm/psi_ms_daq_daq_sm_tb_case_single_window.vhd \
psi_ms_daq_daq_sm/psi_ms_daq_daq_sm_tb_case_single_simple.vhd \
psi_ms_daq_daq_sm/psi_ms_daq_daq_sm_tb_case_priorities.vhd \
psi_ms_daq_daq_sm/psi_ms_daq_daq_sm_tb_case_multi_window.vhd \
psi_ms_daq_daq_sm/psi_ms_daq_daq_sm_tb_case_enable.vhd \
psi_ms_daq_daq_sm/psi_ms_daq_daq_sm_tb_case_irq.vhd \
psi_ms_daq_daq_sm/psi_ms_daq_daq_sm_tb_case_timestamp.vhd \
psi_ms_daq_daq_sm/psi_ms_daq_daq_sm_tb.vhd \
psi_ms_daq_daq_dma/psi_ms_daq_daq_dma_tb_pkg.vhd \
psi_ms_daq_daq_dma/psi_ms_daq_daq_dma_tb_case_unaligned.vhd \
psi_ms_daq_daq_dma/psi_ms_daq_daq_dma_tb_case_no_data_read.vhd \
psi_ms_daq_daq_dma/psi_ms_daq_daq_dma_tb_case_input_empty.vhd \
psi_ms_daq_daq_dma/psi_ms_daq_daq_dma_tb_case_empty_timeout.vhd \
psi_ms_daq_daq_dma/psi_ms_daq_daq_dma_tb_case_data_full.vhd \
psi_ms_daq_daq_dma/psi_ms_daq_daq_dma_tb_case_cmd_full.vhd \
psi_ms_daq_daq_dma/psi_ms_daq_daq_dma_tb_case_aligned.vhd \
psi_ms_daq_daq_dma/psi_ms_daq_daq_dma_tb_case_errors.vhd \
psi_ms_daq_daq_dma/psi_ms_daq_daq_dma_tb.vhd \
psi_ms_daq/psi_ms_daq_tb_pkg.vhd \
psi_ms_daq/psi_ms_daq_tb_str0_pkg.vhd \
psi_ms_daq/psi_ms_daq_tb_str1_pkg.vhd \
psi_ms_daq/psi_ms_daq_tb_str2_pkg.vhd \
psi_ms_daq/psi_ms_daq_tb_str3_pkg.vhd \
psi_ms_daq/psi_ms_daq_tb.vhd \
} -tag tb
#TB Runs
create_tb_run "psi_ms_daq_input_tb"
tb_run_add_arguments \
"-gStreamWidth_g=8 -gVldPulsed=false" \
"-gStreamWidth_g=8 -gVldPulsed=true" \
"-gStreamWidth_g=16 -gVldPulsed=false" \
"-gStreamWidth_g=32 -gVldPulsed=false" \
"-gStreamWidth_g=64 -gVldPulsed=false" \
"-gStreamWidth_g=64 -gVldPulsed=true"
add_tb_run
create_tb_run "psi_ms_daq_daq_sm_tb"
add_tb_run
create_tb_run "psi_ms_daq_daq_dma_tb"
add_tb_run
create_tb_run "psi_ms_daq_tb"
add_tb_run

View File

@@ -1,13 +0,0 @@
#This script setps up Modelsim for interactively
# .. working from the TCL console.
#Import TCL Framework
source ../../../TCL/PsiSim/PsiSim.tcl
namespace import psi::sim::*
#Initialize Simulation
init
#Configure
source ./config.tcl
compile_files -all -clean

View File

@@ -1,24 +0,0 @@
#Load dependencies
source ../../../TCL/PsiSim/PsiSim.tcl
namespace import psi::sim::*
#Initialize Simulation
init
#Configure
source ./config.tcl
#Run Simulation
puts "------------------------------"
puts "-- Compile"
puts "------------------------------"
compile_files -all -clean
puts "------------------------------"
puts "-- Run"
puts "------------------------------"
run_tb -all
puts "------------------------------"
puts "-- Check"
puts "------------------------------"
run_check_errors "###ERROR###"

View File

@@ -1,318 +0,0 @@
------------------------------------------------------------
-- Testbench generated by TbGen.py
------------------------------------------------------------
-- see Library/Python/TbGenerator
------------------------------------------------------------
-- Libraries
------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_common_array_pkg.all;
use work.psi_ms_daq_pkg.all;
library work;
use work.psi_tb_txt_util.all;
use work.psi_tb_compare_pkg.all;
use work.smem_master_types_pkg.all;
use work.psi_ms_daq_tb_pkg.all;
use work.psi_ms_daq_tb_str0_pkg.all;
use work.psi_ms_daq_tb_str1_pkg.all;
use work.psi_ms_daq_tb_str2_pkg.all;
use work.psi_ms_daq_tb_str3_pkg.all;
------------------------------------------------------------
-- Entity Declaration
------------------------------------------------------------
entity psi_ms_daq_tb is
end entity;
------------------------------------------------------------
-- Architecture
------------------------------------------------------------
architecture sim of psi_ms_daq_tb is
-- TB Control
signal TbRunning : boolean := true;
signal PrintIrq_c : boolean := PrintDefault_c;
-- Constants
constant StrCount_c : integer := 4;
constant ClkFreq_c : t_areal := (0=>250.0e6, 1=>125.0e6, 2=>80.0e6, 3=>200.0e6);
-- Port signals
signal Str_Clk : std_logic_vector(StrCount_c-1 downto 0) := (others => '0');
signal Str0_Data : std_logic_vector(7 downto 0) := (others => '0');
signal Str1_Data : std_logic_vector(15 downto 0) := (others => '0');
signal Str2_Data : std_logic_vector(15 downto 0) := (others => '0');
signal Str3_Data : std_logic_vector(31 downto 0) := (others => '0');
signal Timestamp : t_aslv64(StrCount_c-1 downto 0) := (others => (others => '0'));
signal Str_Vld : std_logic_vector(StrCount_c-1 downto 0) := (others => '0');
signal Str_Rdy : std_logic_vector(StrCount_c-1 downto 0) := (others => '0');
signal Str_Trig : std_logic_vector(StrCount_c-1 downto 0) := (others => '0');
signal Tmem_Clk : std_logic := '0';
signal Smem_Clk : std_logic := '0';
signal Tmem_Rst : std_logic := '1';
signal Smem_Rst : std_logic := '1';
signal TmemAcq : TmemRqst_t := TmemRqst_init_c;
signal AcqTmem : TmemResp_t;
signal SmemAcq : FromSmemWr_t := (others => (others => '0'));
signal AcqSmem : ToSmemWr_t;
signal Irq : std_logic := '0';
procedure IrqHandler( signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t) is
variable v : integer;
variable slv : std_logic_vector(31 downto 0);
begin
print("###################################### IRQ Detected #########################################", PrintIrq_c);
wait until rising_edge(clk);
TmemRead32(16#0010#, v, clk, rqst, rsp);
slv := std_logic_vector(to_unsigned(v, 32));
TmemWrite32(16#0010#, v, clk, rqst, rsp);
for i in 0 to StrCount_c-1 loop
if slv(i) = '1' then
case i is
when 0 => Str0Handler(clk, rqst, rsp);
when 1 => Str1Handler(clk, rqst, rsp);
when 2 => Str2Handler(clk, rqst, rsp);
when 3 => Str3Handler(clk, rqst, rsp);
when others => null;
end case;
end if;
end loop;
-- Delay to ensure IRQ is cleared
for i in 0 to 5 loop
wait until rising_edge(clk);
end loop;
end procedure;
begin
------------------------------------------------------------
-- DUT Instantiation
------------------------------------------------------------
i_dut : entity work.psi_ms_daq
generic map (
Streams_g => StrCount_c,
StreamWidth_g => (0=>8, 1=>16, 2=>16, 3=>32),
StreamPrio_g => (0=>1, 1=>3, 2=>2, 3=>2),
StreamBuffer_g => (0=>32, 1=>128, 2=>128, 3=>128),
StreamTimeout_g => (0=>5.0e-6, 1=>1.0e-3, 2=>1.0e-3, 3=>1.0e-3),
StreamClkFreq_g => ClkFreq_c,
StreamTsFifoDepth_g => (0=>16, 1=>16, 2=>16, 3=>16),
StreamUseTs_g => (0=>true, 1=>true, 2=>true, 3=>false),
MaxWindows_g => work.psi_ms_daq_tb_pkg.MaxWindows_c,
MinBurstSize_g => 16,
MaxBurstSize_g => 128
)
port map (
Str_Clk => Str_Clk,
Str_Data(0)(7 downto 0) => Str0_Data,
Str_Data(0)(63 downto 8) => (others => '0'),
Str_Data(1)(15 downto 0) => Str1_Data,
Str_Data(1)(63 downto 16) => (others => '0'),
Str_Data(2)(15 downto 0) => Str2_Data,
Str_Data(2)(63 downto 16) => (others => '0'),
Str_Data(3)(31 downto 0) => Str3_Data,
Str_Data(3)(63 downto 32) => (others => '0'),
Str_Ts => Timestamp,
Str_Vld => Str_Vld,
Str_Rdy => Str_Rdy,
Str_Trig => Str_Trig,
Tmem_Clk => Tmem_Clk,
Tmem_Rst => Tmem_Rst,
Smem_Clk => Smem_Clk,
Smem_Rst => Smem_Rst,
TmemAcq => TmemAcq,
AcqTmem => AcqTmem,
AcqSmem => AcqSmem,
SmemAcq => SmemAcq,
Irq => Irq
);
------------------------------------------------------------
-- Emulate Memory
------------------------------------------------------------
p_mem : process
variable Address_v : integer;
variable Size_v : integer;
begin
while TbRunning loop
wait until (rising_edge(Smem_Clk) and AcqSmem.WREQ = SMEM_REQ_Request_c) or (not TbRunning);
if TbRunning then
wait until rising_edge(Smem_Clk);
Address_v := to_integer(unsigned(AcqSmem.WADD));
Size_v := to_integer(unsigned(AcqSmem.WSIZ));
SmemAcq.WACK <= SMEM_ACK_Grant_c;
wait until rising_edge(Smem_Clk);
SmemAcq.WACK <= SMEM_ACK_Burst_c;
wait until rising_edge(Smem_Clk);
wait until rising_edge(Smem_Clk);
wait until rising_edge(Smem_Clk);
for qw in 0 to Size_v-1 loop
if qw = Size_v-1 then
SmemAcq.WACK <= SMEM_ACK_Done_c;
end if;
wait until rising_edge(Smem_Clk);
for byte in 0 to 7 loop
if AcqSmem.WBE(byte) = '1' then
Memory(Address_v+qw*8+byte) <= AcqSmem.WDAT(byte*8+7 downto byte*8);
end if;
end loop;
end loop;
SmemAcq.WACK <= SMEM_ACK_Idle_c;
wait until rising_edge(Smem_Clk);
end if;
end loop;
wait;
end process;
------------------------------------------------------------
-- Clocks
------------------------------------------------------------
p_clk_smem : process
constant Frequency_c : real := real(200e6);
begin
while TbRunning loop
wait for 0.5*(1 sec)/Frequency_c;
Smem_Clk <= not Smem_Clk;
end loop;
wait;
end process;
p_clk_tmem : process
constant Frequency_c : real := real(166e6);
begin
while TbRunning loop
wait for 0.5*(1 sec)/Frequency_c;
Tmem_Clk <= not Tmem_Clk;
end loop;
wait;
end process;
g_clk_str : for i in 0 to StrCount_c-1 generate
p_clk_str : process
begin
while TbRunning loop
wait for 0.5*(1 sec)/(ClkFreq_c(i)+0.1e6);
Str_Clk(i) <= not Str_Clk(i);
end loop;
wait;
end process;
end generate;
------------------------------------------------------------
-- TMEM Process
------------------------------------------------------------
p_tmem : process
variable StartTime_v : time;
variable Stream1Armed_v : boolean := false;
variable Stream2Armed_v : boolean := false;
begin
print("*** Info ***");
print("This testbench does not print any status information by default (only errors).");
print("To change this behavior, change the constant PrintDefault_c in psi_ms_daq_tb_pkg.");
wait for 1 us;
Tmem_Rst <= '0';
Smem_Rst <= '0';
-- *** Initial Configuration ***
TmemExpect32(16#0010#, 0, Tmem_Clk, TmemAcq, AcqTmem);
TmemWriteAndRead32(16#0014#, 16#000F#, Tmem_Clk, TmemAcq, AcqTmem);
TmemWriteAndRead32(16#0020#, 16#000F#, Tmem_Clk, TmemAcq, AcqTmem);
-- Stream Setup
Str0Setup(Tmem_Clk, TmemAcq, AcqTmem);
Str1Setup(Tmem_Clk, TmemAcq, AcqTmem);
Str2Setup(Tmem_Clk, TmemAcq, AcqTmem);
Str3Setup(Tmem_Clk, TmemAcq, AcqTmem);
-- Enable
TmemWriteAndRead32(16#0000#, 16#0101#, Tmem_Clk, TmemAcq, AcqTmem);
-- *** Run Test ***
StartTime_v := now;
while now < StartTime_v+100 us loop
wait until rising_edge(Tmem_Clk);
-- IRQ Handling
if Irq = '1' then
IrqHandler(Tmem_Clk, TmemAcq, AcqTmem);
end if;
-- Regular actions
Str0Update(Tmem_Clk, TmemAcq, AcqTmem);
Str1Update(Tmem_Clk, TmemAcq, AcqTmem);
Str2Update(Tmem_Clk, TmemAcq, AcqTmem);
Str3Update(Tmem_Clk, TmemAcq, AcqTmem);
end loop;
TbRunning <= false;
-- *** Check end state ***
assert Str0WinCheck >= 4 report "###ERROR###: Stream 0 checks not completed" severity error;
assert Str1WinCheck = 1 report "###ERROR###: Stream 1 checks not completed" severity error;
assert Str2WinCheck = 2 report "###ERROR###: Stream 2 checks not completed" severity error;
assert Str3WinCheck = 2 report "###ERROR###: Stream 3 checks not completed" severity error;
wait;
end process;
------------------------------------------------------------
-- Timestamp Processes
------------------------------------------------------------
g_ts : for i in 0 to StrCount_c-1 generate
p_ts : process
begin
while TbRunning loop
wait until rising_edge(Str_Clk(0));
Timestamp(0) <= std_logic_vector(unsigned(Timestamp(0)) + 1);
end loop;
wait;
end process;
end generate;
------------------------------------------------------------
-- Data Generation Processes
------------------------------------------------------------
p_str0 : process
variable IrqOn : boolean := false;
begin
wait until rising_edge(Str_Clk(0));
while TbRunning loop
Str0Sample(Str_Clk(0), Str_Vld(0), Str_Trig(0), Str0_Data);
end loop;
wait;
end process;
p_str1 : process
begin
Str1Data(Str_Clk(1), Str_Vld(1), Str_Trig(1), Str1_Data);
wait;
end process;
p_str2 : process
begin
Str2Data(Str_Clk(2), Str_Vld(2), Str_Trig(2), Str2_Data);
wait;
end process;
p_str3 : process
begin
Str3Data(Str_Clk(3), Str_Vld(3), Str_Trig(3), Str3_Data);
wait;
end process;
------------------------------------------------------------
-- Check Process
------------------------------------------------------------
end;

View File

@@ -1,483 +0,0 @@
------------------------------------------------------------
-- Libraries
------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_common_array_pkg.all;
use work.psi_ms_daq_pkg.all;
library work;
use work.psi_tb_txt_util.all;
use work.psi_tb_compare_pkg.all;
------------------------------------------------------------
-- Package Header
------------------------------------------------------------
package psi_ms_daq_tb_pkg is
--------------------------------------------------------
-- Global Stuff
--------------------------------------------------------
constant MemSize_c : integer := 16#10000#;
signal Memory : t_aslv8(0 to MemSize_c-1);
constant MaxWindows_c : integer := 16;
constant PrintDefault_c : boolean := false;
--------------------------------------------------------
-- Register MAP
--------------------------------------------------------
constant REG_CONF_REGION : integer := 16#0000#;
constant REG_CONF_GCFG_ADDR : integer := REG_CONF_REGION+16#000#;
constant REG_CONF_GSTAT_ADDR : integer := REG_CONF_REGION+16#004#;
constant REG_CONF_IRQVEC_ADDR : integer := REG_CONF_REGION+16#010#;
constant REG_CONF_IRQENA_ADDR : integer := REG_CONF_REGION+16#014#;
constant REG_CONF_STRENA_ADDR : integer := REG_CONF_REGION+16#020#;
constant REG_CONF_Xn_STEP : integer := 16#10#;
constant REG_CONF_MAXLVLn : integer := 16#200#;
constant REG_CONF_POSTTRIGn : integer := 16#204#;
constant REG_CONF_MODEn : integer := 16#208#;
constant VAL_MODE_RECM_CONT : integer := 0*2**0;
constant VAL_MODE_RECM_TRIGMASK : integer := 1*2**0;
constant VAL_MODE_RECM_SINGLE : integer := 2*2**0;
constant VAL_MODE_RECM_MANUAL : integer := 3*2**0;
constant VAL_MODE_ARM : integer := 1*2**8;
constant VAL_MODE_RECORDING : integer := 1*2**16;
constant REG_CTX_REGION : integer := 16#1000#;
constant REG_CTX_Xn_STEP : integer := 16#20#;
constant REG_CTX_SCFGn : integer := 16#00#;
constant VAL_SCFG_RINGBUF : integer := 1*2**0;
constant VAL_SCFG_OVERWRITE : integer := 1*2**8;
constant SFT_SCFG_WINCNT : integer := 16;
constant SFT_SCFG_WINCUR : integer := 24;
constant MSK_SCFG_WINCUR : integer := 16#1F000000#;
constant REG_CTX_BUFSTARTn : integer := 16#04#;
constant REG_CTX_WINSIZEn : integer := 16#08#;
constant REG_CTX_PTRn : integer := 16#0C#;
constant REG_WIN_REGION : integer := 16#4000#;
constant REG_WIN_STRn_STEP : integer := MaxWindows_c*16#10#;
constant REG_WIN_WINn_STEP : integer := 16#10#;
constant REG_WIN_WINCNT : integer := 16#00#;
constant MSK_WIN_WINCNT_CNT : integer := 16#7FFFFFFF#;
constant REG_WIN_WINLAST : integer := 16#04#;
constant REG_WIN_TSLO : integer := 16#08#;
constant REG_WIN_TSHI : integer := 16#0C#;
--------------------------------------------------------
-- Helper Procedures
--------------------------------------------------------
function IntAnd( int : in integer;
op : in integer) return integer;
procedure print( str : in string;
ena : in boolean);
--------------------------------------------------------
-- TMEM Procedures
--------------------------------------------------------
procedure TmemWrite32( address : in integer;
value : in integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t);
procedure TmemRead32( address : in integer;
value : out integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t);
procedure TmemExpect32( address : in integer;
value : in integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t);
procedure TmemWriteAndRead32( address : in integer;
value : in integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t);
--------------------------------------------------------
-- High Level Procedures
--------------------------------------------------------
procedure HlCheckMaxLvl( str : in integer;
expLevel : in integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t);
procedure HlSetPostTrig( str : in integer;
val : in integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t);
procedure HlSetMode( str : in integer;
val : in integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t);
procedure HlConfStream( str : in integer;
bufstart : in integer;
ringbuf : in boolean;
overwrite : in boolean;
wincnt : in integer;
winsize : in integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t);
procedure HlIsRecording( str : in integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t;
val : out boolean);
procedure HlGetPtr( str : in integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t;
val : out integer);
procedure HlGetMaxLvl( str : in integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t;
val : out integer);
procedure HlGetCurWin( str : in integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t;
val : out integer);
procedure HlGetWinCnt( str : in integer;
win : in integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t;
val : out integer);
procedure HlIsTrigWin( str : in integer;
win : in integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t;
val : out boolean);
procedure HlClrWinCnt( str : in integer;
win : in integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t);
procedure HlGetWinLast( str : in integer;
win : in integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t;
val : out integer);
procedure HlGetTsLo( str : in integer;
win : in integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t;
val : out integer);
procedure HlGetTsHi( str : in integer;
win : in integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t;
val : out integer);
end package;
------------------------------------------------------------
-- Package Body
------------------------------------------------------------
package body psi_ms_daq_tb_pkg is
--------------------------------------------------------
-- Helper Procedures
--------------------------------------------------------
function IntAnd( int : in integer;
op : in integer) return integer is
variable intu, opu : signed(31 downto 0);
begin
intu := to_signed(int, 32);
opu := to_signed(op, 32);
return to_integer(intu and opu);
end function;
procedure print( str : in string;
ena : in boolean) is
begin
if ena then
print(str);
end if;
end procedure;
--------------------------------------------------------
-- TMEM Procedures
--------------------------------------------------------
procedure TmemWrite32( address : in integer;
value : in integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t) is
begin
wait until rising_edge(clk);
rqst.ADD <= std_logic_vector(to_unsigned(address, 24)) and X"FFFFF8";
rqst.ENA <= '1';
rqst.DATW <= (others => '0');
rqst.WE <= (others => '0');
if address mod 8 = 0 then
rqst.DATW(31 downto 0) <= std_logic_vector(to_unsigned(value, 32));
rqst.WE(3 downto 0) <= (others => '1');
else
rqst.DATW(63 downto 32) <= std_logic_vector(to_unsigned(value, 32));
rqst.WE(7 downto 4) <= (others => '1');
end if;
wait until rising_edge(clk);
rqst.ENA <= '0';
rqst.WE <= (others => '0');
end procedure;
procedure TmemRead32( address : in integer;
value : out integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t) is
begin
wait until rising_edge(clk);
rqst.ADD <= std_logic_vector(to_unsigned(address, 24)) and X"FFFFF8";
rqst.ENA <= '1';
wait until rising_edge(clk);
wait until rising_edge(clk);
wait until rising_edge(clk);
if address mod 8 = 0 then
value := to_integer(signed(rsp.DATR(31 downto 0)));
else
value := to_integer(signed(rsp.DATR(63 downto 32)));
end if;
rqst.ENA <= '0';
end procedure;
procedure TmemExpect32( address : in integer;
value : in integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t) is
variable readVal : integer;
begin
TmemRead32(address, readVal, clk, rqst, rsp);
IntCompare(value, readVal, "Unexpected value at address 0x" & to_hstring(to_unsigned(address, 32)));
end procedure;
procedure TmemWriteAndRead32( address : in integer;
value : in integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t) is
begin
TmemWrite32(address, value, clk, rqst, rsp);
wait for 400 ns;
wait until rising_edge(clk);
TmemExpect32(address, value, clk, rqst, rsp);
end procedure;
--------------------------------------------------------
-- High Level Procedures
--------------------------------------------------------
procedure HlCheckMaxLvl( str : in integer;
expLevel : in integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t) is
begin
TmemExpect32(REG_CONF_MAXLVLn+REG_CONF_Xn_STEP*str, expLevel, clk, rqst, rsp);
end procedure;
procedure HlSetPostTrig( str : in integer;
val : in integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t) is
begin
TmemWriteAndRead32(REG_CONF_POSTTRIGn+REG_CONF_Xn_STEP*str, val, clk, rqst, rsp);
end procedure;
procedure HlSetMode( str : in integer;
val : in integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t) is
begin
TmemWrite32(REG_CONF_MODEn+REG_CONF_Xn_STEP*str, val, clk, rqst, rsp);
end procedure;
procedure HlConfStream( str : in integer;
bufstart : in integer;
ringbuf : in boolean;
overwrite : in boolean;
wincnt : in integer;
winsize : in integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t) is
variable v : integer := 0;
begin
TmemWriteAndRead32( REG_CTX_REGION+REG_CTX_BUFSTARTn+REG_CTX_Xn_STEP*str,
bufstart, clk, rqst, rsp);
TmemWriteAndRead32( REG_CTX_REGION+REG_CTX_WINSIZEn+REG_CTX_Xn_STEP*str,
winsize, clk, rqst, rsp);
if ringbuf then
v := v + VAL_SCFG_RINGBUF;
end if;
if overwrite then
v := v + VAL_SCFG_OVERWRITE;
end if;
v := v + (2**SFT_SCFG_WINCNT)*(wincnt-1);
TmemWriteAndRead32( REG_CTX_REGION+REG_CTX_SCFGn+REG_CTX_Xn_STEP*str,
v, clk, rqst, rsp);
end procedure;
procedure HlIsRecording( str : in integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t;
val : out boolean) is
variable v : integer := 0;
begin
TmemRead32( REG_CONF_REGION+REG_CONF_MODEn+REG_CONF_Xn_STEP*str,
v, clk, rqst, rsp);
if IntAnd(v, VAL_MODE_RECORDING) /= 0 then
val := true;
else
val := false;
end if;
end procedure;
procedure HlGetPtr( str : in integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t;
val : out integer) is
begin
TmemRead32( REG_CTX_REGION+REG_CTX_PTRn+REG_CTX_Xn_STEP*str,
val, clk, rqst, rsp);
end procedure;
procedure HlGetMaxLvl( str : in integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t;
val : out integer) is
begin
TmemRead32( REG_CONF_REGION+REG_CONF_MAXLVLn+REG_CONF_Xn_STEP*str,
val, clk, rqst, rsp);
end procedure;
procedure HlGetCurWin( str : in integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t;
val : out integer) is
variable v : integer;
begin
TmemRead32( REG_CTX_REGION+REG_CTX_SCFGn+REG_CTX_Xn_STEP*str,
v, clk, rqst, rsp);
v := IntAnd(v, MSK_SCFG_WINCUR);
v := v / (2**SFT_SCFG_WINCUR);
val := v;
end procedure;
procedure HlGetWinCnt( str : in integer;
win : in integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t;
val : out integer) is
variable v : integer;
begin
TmemRead32( REG_WIN_REGION+REG_WIN_WINCNT+REG_WIN_STRn_STEP*str+REG_WIN_WINn_STEP*win,
v, clk, rqst, rsp);
val := IntAnd(v, MSK_WIN_WINCNT_CNT);
end procedure;
procedure HlIsTrigWin( str : in integer;
win : in integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t;
val : out boolean) is
variable v : integer;
begin
TmemRead32( REG_WIN_REGION+REG_WIN_WINCNT+REG_WIN_STRn_STEP*str+REG_WIN_WINn_STEP*win,
v, clk, rqst, rsp);
val := v < 0;
end procedure;
procedure HlClrWinCnt( str : in integer;
win : in integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t) is
variable v : integer;
begin
TmemWrite32( REG_WIN_REGION+REG_WIN_WINCNT+REG_WIN_STRn_STEP*str+REG_WIN_WINn_STEP*win,
0, clk, rqst, rsp);
end procedure;
procedure HlGetWinLast( str : in integer;
win : in integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t;
val : out integer) is
variable v : integer;
begin
TmemRead32( REG_WIN_REGION+REG_WIN_WINLAST+REG_WIN_STRn_STEP*str+REG_WIN_WINn_STEP*win,
val, clk, rqst, rsp);
end procedure;
procedure HlGetTsLo( str : in integer;
win : in integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t;
val : out integer) is
variable v : integer;
begin
TmemRead32( REG_WIN_REGION+REG_WIN_TSLO+REG_WIN_STRn_STEP*str+REG_WIN_WINn_STEP*win,
val, clk, rqst, rsp);
end procedure;
procedure HlGetTsHi( str : in integer;
win : in integer;
signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t;
val : out integer) is
variable v : integer;
begin
TmemRead32( REG_WIN_REGION+REG_WIN_TSHi+REG_WIN_STRn_STEP*str+REG_WIN_WINn_STEP*win,
val, clk, rqst, rsp);
end procedure;
end;

View File

@@ -1,248 +0,0 @@
------------------------------------------------------------
-- Description
------------------------------------------------------------
-- Stream 0 works in ringbuffer mode (without overwrite). It
-- produces 8-bit data (modulo counter). IRQs are located at samples
-- containing data 30, 60 and 90. IRQs are suppressed until 15 us after
-- simulation to see if IRQ enable works correctly.
-- The IRQ handler also sets the window sample counter to zero to ensure
-- more data can be recorded after the IRQ.
------------------------------------------------------------
-- Libraries
------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_common_array_pkg.all;
use work.psi_ms_daq_pkg.all;
library work;
use work.psi_tb_txt_util.all;
use work.psi_tb_compare_pkg.all;
use work.psi_ms_daq_tb_pkg.all;
------------------------------------------------------------
-- Package Header
------------------------------------------------------------
package psi_ms_daq_tb_str0_pkg is
constant PrintStr0_c : boolean := PrintDefault_c;
-- Memory
constant Str0BufStart_c : integer := 16#1000#;
constant Str0WinSize_c : integer := 100;
constant Str0Windows_c : integer := 3;
alias Memory0 : t_aslv8(0 to Str0WinSize_c*Str0Windows_c) is Memory(Str0BufStart_c to Str0BufStart_c+Str0WinSize_c*Str0Windows_c);
--------------------------------------------------------
-- Persistent State
--------------------------------------------------------
shared variable Str0NextWin : integer := 0;
shared variable Str0WinCheck : integer := 0;
shared variable Str0LastTs : integer;
shared variable Str0IrqOn : boolean := false;
shared variable Str0Disabled : boolean := false;
--------------------------------------------------------
-- Data Generation
--------------------------------------------------------
procedure Str0Sample( signal clk : in std_logic;
signal vld : out std_logic;
signal trig : out std_logic;
signal data : out std_logic_vector(7 downto 0));
--------------------------------------------------------
-- IRQ Handler
--------------------------------------------------------
procedure Str0Handler( signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t);
--------------------------------------------------------
-- Setup
--------------------------------------------------------
procedure Str0Setup( signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t);
--------------------------------------------------------
-- Update
--------------------------------------------------------
procedure Str0Update( signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t);
end package;
------------------------------------------------------------
-- Package Body
------------------------------------------------------------
package body psi_ms_daq_tb_str0_pkg is
--------------------------------------------------------
-- Data Generation
--------------------------------------------------------
procedure Str0Sample( signal clk : in std_logic;
signal vld : out std_logic;
signal trig : out std_logic;
signal data : out std_logic_vector(7 downto 0)) is
begin
vld <= '1';
if (now > 15 us) and (to_integer(unsigned(data)) = 0) then
Str0IrqOn := true;
end if;
case to_integer(unsigned(data)) is
when 30 | 60 | 90 =>
if Str0IrqOn then
trig <= '1';
end if;
when others => null;
end case;
wait until rising_edge(clk);
vld <= '0';
trig <= '0';
data <= std_logic_vector(unsigned(data)+1);
wait until rising_edge(clk);
end procedure;
--------------------------------------------------------
-- IRQ Handler
--------------------------------------------------------
procedure Str0Handler( signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t) is
variable v : integer;
variable curwin : integer;
variable wincnt : integer;
variable winstart, winend : integer;
variable winlast : integer;
variable addr : integer;
variable tslo : integer;
variable firstLoop : boolean := true;
variable HasTrigger : boolean;
begin
print("------------ Stream 0 Handler ------------", PrintStr0_c);
HlGetMaxLvl(0, clk, rqst, rsp, v);
print("MAXLVL: " & to_string(v), PrintStr0_c);
HlGetCurWin(0, clk, rqst, rsp, curwin);
print("CURWIN: " & to_string(curwin), PrintStr0_c);
print("", PrintStr0_c);
if Str0Disabled then
print("Skipped, stream disabled", PrintStr0_c);
print("", PrintStr0_c);
else
HlIsTrigWin(0, Str0NextWin, clk, rqst, rsp, HasTrigger);
-- curwin = nextwin can occur if al lwindows are filled. In all cases we only interpret windows containing triggers.
while ((Str0NextWin /= curwin) or firstLoop) and HasTrigger loop
firstLoop := false;
print("*** Window " & to_string(Str0NextWin) & " / Number: " & to_string(Str0WinCheck) & " ***", PrintStr0_c);
HlGetWinCnt(0, Str0NextWin, clk, rqst, rsp, wincnt);
print("WINCNT: " & to_string(wincnt), PrintStr0_c);
HlClrWinCnt(0, Str0NextWin, clk, rqst, rsp);
HlGetWinLast(0, Str0NextWin, clk, rqst, rsp, winlast);
print("WINLAST: " & to_string(winlast), PrintStr0_c);
HlGetTsLo(0, Str0NextWin, clk, rqst, rsp, tslo);
print("WINTSLO: " & to_string(tslo), PrintStr0_c);
HlGetTsHi(0, Str0NextWin, clk, rqst, rsp, v);
print("WINTSHI: " & to_string(v), PrintStr0_c);
winstart := Str0BufStart_c + Str0NextWin*Str0WinSize_c;
winend := winstart + Str0WinSize_c - 1;
case Str0WinCheck is
when 0 =>
-- Windows full because dat received for quite some time
IntCompare(Str0WinSize_c, wincnt, "Stream0: WINCNT wrong");
-- Check Values
addr := winlast;
for i in 256+30+3-99 to 256+30+3 loop
if addr = winend then
addr := winstart;
else
addr := addr + 1;
end if;
StdlvCompareInt (i mod 256, Memory(addr), "Stream0: Wrong value at 0x" & to_hstring(to_unsigned(addr,32)), false);
end loop;
when 1 =>
-- Trigger following each other with 30 samples difference
IntCompare(30, wincnt, "Stream0: WINCNT wrong");
IntCompare(30*2, tslo-Str0LastTs, "Stream0: TS difference wrong");
-- Check Values
addr := winstart;
for i in 34 to 63 loop
StdlvCompareInt (i, Memory(addr), "Stream0: Wrong value", false);
addr := addr + 1; -- does never wrap
end loop;
when 2 =>
-- Trigger following each other with 30 samples difference
IntCompare(30, wincnt, "Stream0: WINCNT wrong");
IntCompare(30*2, tslo-Str0LastTs, "Stream0: TS difference wrong");
-- Check Values
addr := winstart;
for i in 64 to 93 loop
StdlvCompareInt (i, Memory(addr), "Stream0: Wrong value", false);
addr := addr + 1; -- does never wrap
end loop;
when 3 =>
-- Full buffer recorded after emptying first buffer
IntCompare(100, wincnt, "Stream0: WINCNT wrong");
IntCompare((256-2*30)*2, tslo-Str0LastTs, "Stream0: TS difference wrong");
-- Disable stream IRQ
TmemRead32(REG_CONF_IRQENA_ADDR, v, clk, rqst, rsp);
v := IntAnd(v, 16#0FE#);
TmemWrite32(REG_CONF_IRQENA_ADDR, v, clk, rqst, rsp);
TmemRead32(REG_CONF_STRENA_ADDR, v, clk, rqst, rsp);
v := IntAnd(v, 16#0FE#);
TmemWrite32(REG_CONF_STRENA_ADDR, v, clk, rqst, rsp);
Str0Disabled := true;
-- Check Values
addr := winlast + 1;
for i in 256+30+3-99 to 256+30+3 loop
StdlvCompareInt (i mod 256, Memory(addr), "Stream0: Wrong value", false);
if addr = winend then
addr := winstart;
else
addr := addr + 1;
end if;
end loop;
when others => null;
end case;
print("", PrintStr0_c);
Str0LastTs := tslo;
Str0NextWin := (Str0NextWin + 1) mod 3;
Str0WinCheck := Str0WinCheck + 1;
end loop;
end if;
end procedure;
--------------------------------------------------------
-- Setup
--------------------------------------------------------
procedure Str0Setup( signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t) is
begin
HlCheckMaxLvl(0, 0, clk, rqst, rsp);
HlSetPostTrig(0, 3, clk, rqst, rsp);
HlSetMode(0, VAL_MODE_RECM_CONT, clk, rqst, rsp);
HlConfStream( str => 0, bufstart => Str0BufStart_c, ringbuf => true, overwrite => false, wincnt => Str0Windows_c, winsize => Str0WinSize_c,
clk => clk, rqst => rqst, rsp => rsp);
end procedure;
--------------------------------------------------------
-- Update
--------------------------------------------------------
procedure Str0Update( signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t) is
begin
end;
end;

View File

@@ -1,171 +0,0 @@
------------------------------------------------------------
-- Description
------------------------------------------------------------
-- Stream 1 works in manual recording mode. The data is arriving
-- in bursts (samples back-to-back withing bursts) and does
-- not contain any trigger events.
------------------------------------------------------------
-- Libraries
------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_common_array_pkg.all;
use work.psi_ms_daq_pkg.all;
library work;
use work.psi_tb_txt_util.all;
use work.psi_tb_compare_pkg.all;
use work.psi_ms_daq_tb_pkg.all;
------------------------------------------------------------
-- Package Header
------------------------------------------------------------
package psi_ms_daq_tb_str1_pkg is
constant PrintStr1_c : boolean := PrintDefault_c;
-- Memory
constant Str1BufStart_c : integer := 16#2000#;
constant Str1WinSize_c : integer := 500;
constant Str1Windows_c : integer := 1;
alias Memory1 : t_aslv8(0 to Str1WinSize_c*Str1Windows_c) is Memory(Str1BufStart_c to Str1BufStart_c+Str1WinSize_c*Str1Windows_c);
--------------------------------------------------------
-- Persistent State
--------------------------------------------------------
shared variable Str1WinCheck : integer := 0;
shared variable Str1DataCnt : integer := 0;
--------------------------------------------------------
-- Data Generation
--------------------------------------------------------
procedure Str1Data( signal clk : in std_logic;
signal vld : out std_logic;
signal trig : out std_logic;
signal data : out std_logic_vector(15 downto 0));
--------------------------------------------------------
-- IRQ Handler
--------------------------------------------------------
procedure Str1Handler( signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t);
--------------------------------------------------------
-- Setup
--------------------------------------------------------
procedure Str1Setup( signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t);
--------------------------------------------------------
-- Update
--------------------------------------------------------
procedure Str1Update( signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t);
end package;
------------------------------------------------------------
-- Package Body
------------------------------------------------------------
package body psi_ms_daq_tb_str1_pkg is
--------------------------------------------------------
-- Data Generation
--------------------------------------------------------
procedure Str1Data( signal clk : in std_logic;
signal vld : out std_logic;
signal trig : out std_logic;
signal data : out std_logic_vector(15 downto 0)) is
begin
while now < 10 us loop
wait until rising_edge(clk);
end loop;
for i in 0 to 19 loop
vld <= '1';
for k in 0 to 49 loop
data <= std_logic_vector(to_unsigned(Str1DataCnt, 16));
Str1DataCnt := Str1DataCnt + 1;
wait until rising_edge(clk);
end loop;
vld <= '0';
wait for 1 us;
wait until rising_edge(clk);
end loop;
end procedure;
--------------------------------------------------------
-- IRQ Handler
--------------------------------------------------------
procedure Str1Handler( signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t) is
variable v : integer;
variable curwin : integer;
variable wincnt : integer;
variable winlast : integer;
variable valRead : unsigned(15 downto 0);
begin
print("------------ Stream 1 Handler ------------", PrintStr1_c);
HlGetMaxLvl(1, clk, rqst, rsp, v);
print("MAXLVL: " & to_string(v), PrintStr1_c);
HlGetPtr(1, clk, rqst, rsp, v);
print("PTR: " & to_string(v), PrintStr1_c);
HlGetCurWin(1, clk, rqst, rsp, curwin);
print("CURWIN: " & to_string(curwin), PrintStr1_c);
IntCompare(0, curwin, "Stream1: CURWIN wrong");
-- Check window content
HlGetWinCnt(1, 0, clk, rqst, rsp, wincnt);
print("WINCNT: " & to_string(wincnt), PrintStr1_c);
IntCompare(250, wincnt, "Stream1:WINCNT wrong");
HlGetWinLast(1, 0, clk, rqst, rsp, winlast);
print("WINLAST: " & to_string(winlast), PrintStr1_c);
IntCompare(16#2000#+498, winlast, "Stream1:WINLAST wrong");
for spl in 0 to 249 loop
valRead(7 downto 0) := unsigned(Memory1(spl*2));
valRead(15 downto 8) := unsigned(Memory1(spl*2+1));
-- first 100 samples are before arming
StdlvCompareInt (spl+100, std_logic_vector(valRead), "Stream1:Wrong value", false);
end loop;
print("", PrintStr1_c);
Str1WinCheck := Str1WinCheck + 1;
end procedure;
--------------------------------------------------------
-- Setup
--------------------------------------------------------
procedure Str1Setup( signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t) is
begin
HlCheckMaxLvl(1, 0, clk, rqst, rsp);
HlSetPostTrig(1, 250, clk, rqst, rsp);
HlSetMode(1, VAL_MODE_RECM_MANUAL, clk, rqst, rsp);
HlConfStream( str => 1, bufstart => Str1BufStart_c, ringbuf => false, overwrite => false, wincnt => Str1Windows_c, winsize => Str1WinSize_c,
clk => clk, rqst => rqst, rsp => rsp);
end procedure;
--------------------------------------------------------
-- Update
--------------------------------------------------------
procedure Str1Update( signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t) is
variable Stream1Armed_v : boolean := false;
begin
-- ARM recorder at required point in time
if Str1DataCnt = 99 and not Stream1Armed_v then
Stream1Armed_v := true;
HlSetMode(1, VAL_MODE_RECM_MANUAL + VAL_MODE_ARM, clk, rqst, rsp);
end if;
end;
end;

View File

@@ -1,202 +0,0 @@
------------------------------------------------------------
-- Description
------------------------------------------------------------
-- Stream 2 works in siingle recording mode. The data is arriving
-- in bursts (samples back-to-back withing bursts) and does
-- contain trigger events at the really begining (sample 0).
------------------------------------------------------------
-- Libraries
------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_common_array_pkg.all;
use work.psi_ms_daq_pkg.all;
library work;
use work.psi_tb_txt_util.all;
use work.psi_tb_compare_pkg.all;
use work.psi_ms_daq_tb_pkg.all;
------------------------------------------------------------
-- Package Header
------------------------------------------------------------
package psi_ms_daq_tb_str2_pkg is
constant PrintStr2_c : boolean := PrintDefault_c;
-- Memory
constant Str2BufStart_c : integer := 16#3000#;
constant Str2WinSize_c : integer := 256;
constant Str2Windows_c : integer := 3;
constant Str2PostTrig_c : integer := 127;
alias Memory2 : t_aslv8(0 to Str2WinSize_c*Str2Windows_c) is Memory(Str2BufStart_c to Str2BufStart_c+Str2WinSize_c*Str2Windows_c);
--------------------------------------------------------
-- Persistent State
--------------------------------------------------------
shared variable Str2FrameCnt : integer := 0;
shared variable Str2SplCnt : integer := 0;
shared variable Str2WinCheck : integer := 0;
shared variable Str2ExpFrame : integer := 0;
shared variable Stream2Armed_v : boolean := false;
--------------------------------------------------------
-- Data Generation
--------------------------------------------------------
procedure Str2Data( signal clk : in std_logic;
signal vld : out std_logic;
signal trig : out std_logic;
signal data : out std_logic_vector(15 downto 0));
--------------------------------------------------------
-- IRQ Handler
--------------------------------------------------------
procedure Str2Handler( signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t);
--------------------------------------------------------
-- Setup
--------------------------------------------------------
procedure Str2Setup( signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t);
--------------------------------------------------------
-- Update
--------------------------------------------------------
procedure Str2Update( signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t);
end package;
------------------------------------------------------------
-- Package Body
------------------------------------------------------------
package body psi_ms_daq_tb_str2_pkg is
--------------------------------------------------------
-- Data Generation
--------------------------------------------------------
procedure Str2Data( signal clk : in std_logic;
signal vld : out std_logic;
signal trig : out std_logic;
signal data : out std_logic_vector(15 downto 0)) is
begin
while now < 8.5 us loop
wait until rising_edge(clk);
end loop;
for i in 0 to 19 loop
vld <= '1';
Str2SplCnt := 0;
trig <= '1';
for k in 0 to 199 loop
data <= std_logic_vector(to_unsigned(Str2FrameCnt*256+Str2SplCnt, 16));
Str2SplCnt := Str2SplCnt + 1;
wait until rising_edge(clk);
trig <= '0';
end loop;
Str2FrameCnt := Str2FrameCnt + 1;
vld <= '0';
wait for 1 us;
wait until rising_edge(clk);
end loop;
end procedure;
--------------------------------------------------------
-- IRQ Handler
--------------------------------------------------------
procedure Str2Handler( signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t) is
variable v : integer;
variable curwin : integer;
variable wincnt : integer;
variable spladdr : integer;
variable splNr : integer;
variable valRead : unsigned(15 downto 0);
variable splInWin : integer;
variable isTrig : boolean;
begin
print("------------ Stream 2 Handler ------------", PrintStr2_c);
HlGetMaxLvl(2, clk, rqst, rsp, v);
print("MAXLVL: " & to_string(v), PrintStr2_c);
HlGetPtr(2, clk, rqst, rsp, v);
print("PTR: " & to_string(v), PrintStr2_c);
HlGetCurWin(2, clk, rqst, rsp, curwin);
print("CURWIN: " & to_string(curwin), PrintStr2_c);
-- Calculate window to read
if curwin = 0 then
curwin := Str2Windows_c-1;
else
curwin := curwin-1;
end if;
-- Read window data
-- Check if recording is finished
HlIsTrigWin(2, curwin, clk, rqst, rsp, isTrig);
if not isTrig then
print("Skipped: not a trigger window", PrintStr2_c);
else
-- Check Data (last 128 samples)
splNr := Str2PostTrig_c;
while splNr >= 0 loop
print("check window " & to_string(curwin), PrintStr2_c);
HlGetWinLast(2, curwin, clk, rqst, rsp, spladdr);
print("WINLAST: " & to_string(spladdr), PrintStr2_c);
while (splNr >= 0) and (spladdr >= Str2BufStart_c+curwin*Str2WinSize_c) loop
StdlvCompareInt(splNr, Memory(spladdr), "Stream2: Sample " & to_string(Str2ExpFrame) & ":" & to_string(splNr) & " wrong CNT", false);
StdlvCompareInt(Str2ExpFrame, Memory(spladdr+1), "Stream2: Sample " & to_string(Str2ExpFrame) & ":" & to_string(splNr) & " wrong FRAME", false);
spladdr := spladdr - 2;
splNr := splNr - 1;
end loop;
-- Next Window
if curwin = 0 then
curwin := Str2Windows_c-1;
else
curwin := curwin-1;
end if;
end loop;
Str2WinCheck := Str2WinCheck + 1;
end if;
print("", PrintStr2_c);
end procedure;
--------------------------------------------------------
-- Setup
--------------------------------------------------------
procedure Str2Setup( signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t) is
begin
HlCheckMaxLvl(2, 0, clk, rqst, rsp);
HlSetPostTrig(2, Str2PostTrig_c, clk, rqst, rsp);
HlSetMode(2, VAL_MODE_RECM_SINGLE, clk, rqst, rsp);
HlConfStream( str => 2, bufstart => Str2BufStart_c, ringbuf => false, overwrite => true, wincnt => Str2Windows_c, winsize => Str2WinSize_c,
clk => clk, rqst => rqst, rsp => rsp);
end procedure;
--------------------------------------------------------
-- Update
--------------------------------------------------------
procedure Str2Update( signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t) is
begin
-- ARM Stream 2 after 3 bursts
if ((Str2FrameCnt = 2) or (Str2FrameCnt = 12)) and
(Str2SplCnt >= 80) and (Str2SplCnt <= 150) and not Stream2Armed_v then
Stream2Armed_v := true;
HlSetMode(2, VAL_MODE_RECM_SINGLE + VAL_MODE_ARM, clk, rqst, rsp);
Str2ExpFrame := Str2FrameCnt + 1;
elsif Str2FrameCnt = 11 then
Stream2Armed_v := false;
end if;
end;
end;

View File

@@ -1,213 +0,0 @@
------------------------------------------------------------
-- Description
------------------------------------------------------------
------------------------------------------------------------
-- Libraries
------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_common_array_pkg.all;
use work.psi_ms_daq_pkg.all;
library work;
use work.psi_tb_txt_util.all;
use work.psi_tb_compare_pkg.all;
use work.psi_ms_daq_tb_pkg.all;
------------------------------------------------------------
-- Package Header
------------------------------------------------------------
package psi_ms_daq_tb_str3_pkg is
constant PrintStr3_c : boolean := PrintDefault_c;
-- Memory
constant Str3BufStart_c : integer := 16#4000#;
constant Str3WinSize_c : integer := 1024;
constant Str3Windows_c : integer := 3;
constant Str3PostTrig_c : integer := 9;
constant Str3TrigPos_c : integer := 100;
alias Memory3 : t_aslv8(0 to Str3WinSize_c*Str3Windows_c) is Memory(Str3BufStart_c to Str3BufStart_c+Str3WinSize_c*Str3Windows_c);
--------------------------------------------------------
-- Persistent State
--------------------------------------------------------
shared variable Str3ExpFrame : integer := 0;
shared variable Str3FrameCnt : integer := 0;
shared variable Str3SplCnt : integer := 0;
shared variable Str3WinCheck : integer := 0;
shared variable Stream3Armed_v : boolean := false;
--------------------------------------------------------
-- Data Generation
--------------------------------------------------------
procedure Str3Data( signal clk : in std_logic;
signal vld : out std_logic;
signal trig : out std_logic;
signal data : out std_logic_vector(31 downto 0));
--------------------------------------------------------
-- IRQ Handler
--------------------------------------------------------
procedure Str3Handler( signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t);
--------------------------------------------------------
-- Setup
--------------------------------------------------------
procedure Str3Setup( signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t);
--------------------------------------------------------
-- Update
--------------------------------------------------------
procedure Str3Update( signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t);
end package;
------------------------------------------------------------
-- Package Body
------------------------------------------------------------
package body psi_ms_daq_tb_str3_pkg is
--------------------------------------------------------
-- Data Generation
--------------------------------------------------------
procedure Str3Data( signal clk : in std_logic;
signal vld : out std_logic;
signal trig : out std_logic;
signal data : out std_logic_vector(31 downto 0)) is
begin
while now < 8 us loop
wait until rising_edge(clk);
end loop;
for i in 0 to 9 loop
vld <= '1';
Str3SplCnt := 0;
for k in 0 to 999 loop
data <= std_logic_vector(to_unsigned(Str3FrameCnt*2**16+Str3SplCnt, 32));
if Str3SplCnt = Str3TrigPos_c then
trig <= '1';
else
trig <= '0';
end if;
Str3SplCnt := Str3SplCnt + 1;
wait until rising_edge(clk);
end loop;
Str3FrameCnt := Str3FrameCnt + 1;
vld <= '0';
wait for 1 us;
wait until rising_edge(clk);
end loop;
end procedure;
--------------------------------------------------------
-- IRQ Handler
--------------------------------------------------------
procedure Str3Handler( signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t) is
variable v : integer;
variable curwin : integer;
variable wincnt : integer;
variable winlast : integer;
variable spladdr : integer;
variable splNr : integer;
variable valRead : unsigned(15 downto 0);
variable splInWin : integer;
variable isRecording : boolean;
begin
print("------------ Stream 3 Handler ------------", PrintStr3_c);
HlGetMaxLvl(3, clk, rqst, rsp, v);
print("MAXLVL: " & to_string(v), PrintStr3_c);
HlGetPtr(3, clk, rqst, rsp, v);
print("PTR: " & to_string(v), PrintStr3_c);
HlGetCurWin(3, clk, rqst, rsp, curwin);
print("CURWIN: " & to_string(curwin), PrintStr3_c);
-- Calculate window to read
if curwin = 0 then
curwin := Str3Windows_c-1;
else
curwin := curwin-1;
end if;
-- Check Data from this frame
splNr := Str3TrigPos_c+Str3PostTrig_c;
-- Read window data (Post-Trigger, from this window)
print("check post-trigger", PrintStr3_c);
HlGetWinLast(3, curwin, clk, rqst, rsp, winlast);
print("WINLAST: " & to_string(winlast), PrintStr3_c);
spladdr := winlast;
while splNr >= 0 loop
StdlvCompareInt(splNr, Memory(spladdr+1) & Memory(spladdr), "Stream3: Sample " & to_string(Str3ExpFrame) & ":" & to_string(splNr) & " wrong CNT", false);
StdlvCompareInt(Str3ExpFrame, Memory(spladdr+3) & Memory(spladdr+2), "Stream3: Sample " & to_string(Str3ExpFrame) & ":" & to_string(splNr) & " wrong FRAME", false);
-- Wraparound
if spladdr = Str3BufStart_c+curwin*Str3WinSize_c then
spladdr := Str3BufStart_c+(curwin+1)*Str3WinSize_c-4;
-- Normal Counting
else
spladdr := spladdr - 4;
end if;
splNr := splNr - 1;
end loop;
-- Read window data (Pre-Trigger, from last window)
print("check pre-trigger", PrintStr3_c);
splNr := 999;
while spladdr /= winlast loop
StdlvCompareInt(splNr, Memory(spladdr+1) & Memory(spladdr), "Stream3: Sample " & to_string(Str3ExpFrame-1) & ":" & to_string(splNr) & " wrong CNT", false);
StdlvCompareInt(Str3ExpFrame-1, Memory(spladdr+3) & Memory(spladdr+2), "Stream3: Sample " & to_string(Str3ExpFrame-1) & ":" & to_string(splNr) & " wrong FRAME", false);
-- Wraparound
if spladdr = Str3BufStart_c+curwin*Str3WinSize_c then
spladdr := Str3BufStart_c+(curwin+1)*Str3WinSize_c-4;
-- Normal Counting
else
spladdr := spladdr - 4;
end if;
splNr := splNr - 1;
end loop;
Str3WinCheck := Str3WinCheck + 1;
print("", PrintStr3_c);
end procedure;
--------------------------------------------------------
-- Setup
--------------------------------------------------------
procedure Str3Setup( signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t) is
begin
HlCheckMaxLvl(3, 0, clk, rqst, rsp);
HlSetPostTrig(3, Str3PostTrig_c, clk, rqst, rsp);
HlSetMode(3, VAL_MODE_RECM_TRIGMASK, clk, rqst, rsp);
HlConfStream( str => 3, bufstart => Str3BufStart_c, ringbuf => true, overwrite => true, wincnt => Str3Windows_c, winsize => Str3WinSize_c,
clk => clk, rqst => rqst, rsp => rsp);
end procedure;
--------------------------------------------------------
-- Update
--------------------------------------------------------
procedure Str3Update( signal clk : in std_logic;
signal rqst : out TmemRqst_t;
signal rsp : in TmemResp_t) is
begin
if ((Str3FrameCnt = 2) or (Str3FrameCnt = 7))
and not Stream3Armed_v then
HlSetMode(3, VAL_MODE_RECM_TRIGMASK + VAL_MODE_ARM, clk, rqst, rsp);
Stream3Armed_v := true;
Str3ExpFrame := Str3FrameCnt;
elsif Str3FrameCnt = 6 then
Stream3Armed_v := false;
end if;
end procedure;
end;

View File

@@ -1,395 +0,0 @@
------------------------------------------------------------
-- Testbench generated by TbGen.py
------------------------------------------------------------
-- see Library/Python/TbGenerator
------------------------------------------------------------
-- Libraries
------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_common_logic_pkg.all;
use work.psi_common_array_pkg.all;
use work.psi_ms_daq_pkg.all;
library work;
use work.psi_tb_txt_util.all;
use work.psi_tb_compare_pkg.all;
use work.psi_tb_activity_pkg.all;
library work;
use work.psi_ms_daq_daq_dma_tb_pkg.all;
library work;
use work.psi_ms_daq_daq_dma_tb_case_aligned.all;
use work.psi_ms_daq_daq_dma_tb_case_unaligned.all;
use work.psi_ms_daq_daq_dma_tb_case_no_data_read.all;
use work.psi_ms_daq_daq_dma_tb_case_input_empty.all;
use work.psi_ms_daq_daq_dma_tb_case_empty_timeout.all;
use work.psi_ms_daq_daq_dma_tb_case_cmd_full.all;
use work.psi_ms_daq_daq_dma_tb_case_data_full.all;
use work.psi_ms_daq_daq_dma_tb_case_errors.all;
------------------------------------------------------------
-- Entity Declaration
------------------------------------------------------------
entity psi_ms_daq_daq_dma_tb is
end entity;
------------------------------------------------------------
-- Architecture
------------------------------------------------------------
architecture sim of psi_ms_daq_daq_dma_tb is
-- *** Fixed Generics ***
constant Streams_g : positive := 4;
-- *** Not Assigned Generics (default values) ***
-- *** Exported Generics ***
constant Generics_c : Generics_t := (
Dummy => true);
-- *** TB Control ***
signal TbRunning : boolean := True;
signal NextCase : integer := -1;
signal ProcessDone : std_logic_vector(0 to 3) := (others => '0');
constant AllProcessesDone_c : std_logic_vector(0 to 3) := (others => '1');
constant TbProcNr_control_c : integer := 0;
constant TbProcNr_input_c : integer := 1;
constant TbProcNr_mem_cmd_c : integer := 2;
constant TbProcNr_mem_dat_c : integer := 3;
-- *** DUT Signals ***
signal Clk : std_logic := '1';
signal Rst : std_logic := '1';
signal DaqSm_Cmd : DaqSm2DaqDma_Cmd_t;
signal DaqSm_Cmd_Vld : std_logic := '0';
signal DaqSm_Resp : DaqDma2DaqSm_Resp_t;
signal DaqSm_Resp_Vld : std_logic := '0';
signal DaqSm_Resp_Rdy : std_logic := '0';
signal DaqSm_HasLast : std_logic_vector(Streams_g-1 downto 0) := (others => '0');
signal Inp_Vld : std_logic_vector(Streams_g-1 downto 0) := (others => '0');
signal Inp_Rdy : std_logic_vector(Streams_g-1 downto 0) := (others => '0');
signal Inp_Data : Input2Daq_Data_a(Streams_g-1 downto 0);
signal Mem_CmdAddr : std_logic_vector(31 downto 0) := (others => '0');
signal Mem_CmdSize : std_logic_vector(31 downto 0) := (others => '0');
signal Mem_CmdVld : std_logic := '0';
signal Mem_CmdRdy : std_logic := '0';
signal Mem_DatData : std_logic_vector(63 downto 0) := (others => '0');
signal Mem_DatVld : std_logic := '0';
signal Mem_DatRdy : std_logic := '0';
begin
------------------------------------------------------------
-- DUT Instantiation
------------------------------------------------------------
i_dut : entity work.psi_ms_daq_daq_dma
generic map (
Streams_g => Streams_g
)
port map (
Clk => Clk,
Rst => Rst,
DaqSm_Cmd => DaqSm_Cmd,
DaqSm_Cmd_Vld => DaqSm_Cmd_Vld,
DaqSm_Resp => DaqSm_Resp,
DaqSm_Resp_Vld => DaqSm_Resp_Vld,
DaqSm_Resp_Rdy => DaqSm_Resp_Rdy,
DaqSm_HasLast => DaqSm_HasLast,
Inp_Vld => Inp_Vld,
Inp_Rdy => Inp_Rdy,
Inp_Data => Inp_Data,
Mem_CmdAddr => Mem_CmdAddr,
Mem_CmdSize => Mem_CmdSize,
Mem_CmdVld => Mem_CmdVld,
Mem_CmdRdy => Mem_CmdRdy,
Mem_DatData => Mem_DatData,
Mem_DatVld => Mem_DatVld,
Mem_DatRdy => Mem_DatRdy
);
------------------------------------------------------------
-- Testbench Control !DO NOT EDIT!
------------------------------------------------------------
p_tb_control : process
begin
-- aligned
NextCase <= 0;
wait until ProcessDone = AllProcessesDone_c;
-- unaligned
NextCase <= 1;
wait until ProcessDone = AllProcessesDone_c;
-- no_data_read
NextCase <= 2;
wait until ProcessDone = AllProcessesDone_c;
-- input_empty
NextCase <= 3;
wait until ProcessDone = AllProcessesDone_c;
-- empty_timeout
NextCase <= 4;
wait until ProcessDone = AllProcessesDone_c;
-- cmd_full
NextCase <= 5;
wait until ProcessDone = AllProcessesDone_c;
-- data_full
NextCase <= 6;
wait until ProcessDone = AllProcessesDone_c;
-- errors
NextCase <= 7;
wait until ProcessDone = AllProcessesDone_c;
TbRunning <= false;
wait;
end process;
------------------------------------------------------------
-- Clocks !DO NOT EDIT!
------------------------------------------------------------
p_clock_Clk : process
constant Frequency_c : real := real(200e6);
begin
while TbRunning loop
wait for 0.5*(1 sec)/Frequency_c;
Clk <= not Clk;
end loop;
wait;
end process;
------------------------------------------------------------
-- Resets
------------------------------------------------------------
p_rst_Rst : process
begin
wait for 1 us;
-- Wait for two clk edges to ensure reset is active for at least one edge
wait until rising_edge(Clk);
wait until rising_edge(Clk);
wait;
end process;
------------------------------------------------------------
-- Processes !DO NOT EDIT!
------------------------------------------------------------
-- *** control ***
p_control : process
begin
-- aligned
wait until NextCase = 0;
ProcessDone(TbProcNr_control_c) <= '0';
work.psi_ms_daq_daq_dma_tb_case_aligned.control(Clk, Rst, DaqSm_Cmd, DaqSm_Cmd_Vld, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, DaqSm_HasLast, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_control_c) <= '1';
-- unaligned
wait until NextCase = 1;
ProcessDone(TbProcNr_control_c) <= '0';
work.psi_ms_daq_daq_dma_tb_case_unaligned.control(Clk, Rst, DaqSm_Cmd, DaqSm_Cmd_Vld, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, DaqSm_HasLast, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_control_c) <= '1';
-- no_data_read
wait until NextCase = 2;
ProcessDone(TbProcNr_control_c) <= '0';
work.psi_ms_daq_daq_dma_tb_case_no_data_read.control(Clk, Rst, DaqSm_Cmd, DaqSm_Cmd_Vld, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, DaqSm_HasLast, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_control_c) <= '1';
-- input_empty
wait until NextCase = 3;
ProcessDone(TbProcNr_control_c) <= '0';
work.psi_ms_daq_daq_dma_tb_case_input_empty.control(Clk, Rst, DaqSm_Cmd, DaqSm_Cmd_Vld, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, DaqSm_HasLast, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_control_c) <= '1';
-- empty_timeout
wait until NextCase = 4;
ProcessDone(TbProcNr_control_c) <= '0';
work.psi_ms_daq_daq_dma_tb_case_empty_timeout.control(Clk, Rst, DaqSm_Cmd, DaqSm_Cmd_Vld, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, DaqSm_HasLast, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_control_c) <= '1';
-- cmd_full
wait until NextCase = 5;
ProcessDone(TbProcNr_control_c) <= '0';
work.psi_ms_daq_daq_dma_tb_case_cmd_full.control(Clk, Rst, DaqSm_Cmd, DaqSm_Cmd_Vld, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, DaqSm_HasLast, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_control_c) <= '1';
-- data_full
wait until NextCase = 6;
ProcessDone(TbProcNr_control_c) <= '0';
work.psi_ms_daq_daq_dma_tb_case_data_full.control(Clk, Rst, DaqSm_Cmd, DaqSm_Cmd_Vld, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, DaqSm_HasLast, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_control_c) <= '1';
-- errors
wait until NextCase = 7;
ProcessDone(TbProcNr_control_c) <= '0';
work.psi_ms_daq_daq_dma_tb_case_errors.control(Clk, Rst, DaqSm_Cmd, DaqSm_Cmd_Vld, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, DaqSm_HasLast, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_control_c) <= '1';
wait;
end process;
-- *** input ***
p_input : process
begin
-- aligned
wait until NextCase = 0;
ProcessDone(TbProcNr_input_c) <= '0';
work.psi_ms_daq_daq_dma_tb_case_aligned.input(Clk, Inp_Vld, Inp_Rdy, Inp_Data, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_input_c) <= '1';
-- unaligned
wait until NextCase = 1;
ProcessDone(TbProcNr_input_c) <= '0';
work.psi_ms_daq_daq_dma_tb_case_unaligned.input(Clk, Inp_Vld, Inp_Rdy, Inp_Data, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_input_c) <= '1';
-- no_data_read
wait until NextCase = 2;
ProcessDone(TbProcNr_input_c) <= '0';
work.psi_ms_daq_daq_dma_tb_case_no_data_read.input(Clk, Inp_Vld, Inp_Rdy, Inp_Data, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_input_c) <= '1';
-- input_empty
wait until NextCase = 3;
ProcessDone(TbProcNr_input_c) <= '0';
work.psi_ms_daq_daq_dma_tb_case_input_empty.input(Clk, Inp_Vld, Inp_Rdy, Inp_Data, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_input_c) <= '1';
-- empty_timeout
wait until NextCase = 4;
ProcessDone(TbProcNr_input_c) <= '0';
work.psi_ms_daq_daq_dma_tb_case_empty_timeout.input(Clk, Inp_Vld, Inp_Rdy, Inp_Data, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_input_c) <= '1';
-- cmd_full
wait until NextCase = 5;
ProcessDone(TbProcNr_input_c) <= '0';
work.psi_ms_daq_daq_dma_tb_case_cmd_full.input(Clk, Inp_Vld, Inp_Rdy, Inp_Data, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_input_c) <= '1';
-- data_full
wait until NextCase = 6;
ProcessDone(TbProcNr_input_c) <= '0';
work.psi_ms_daq_daq_dma_tb_case_data_full.input(Clk, Inp_Vld, Inp_Rdy, Inp_Data, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_input_c) <= '1';
-- errors
wait until NextCase = 7;
ProcessDone(TbProcNr_input_c) <= '0';
work.psi_ms_daq_daq_dma_tb_case_errors.input(Clk, Inp_Vld, Inp_Rdy, Inp_Data, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_input_c) <= '1';
wait;
end process;
-- *** mem_cmd ***
p_mem_cmd : process
begin
-- aligned
wait until NextCase = 0;
ProcessDone(TbProcNr_mem_cmd_c) <= '0';
work.psi_ms_daq_daq_dma_tb_case_aligned.mem_cmd(Clk, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_mem_cmd_c) <= '1';
-- unaligned
wait until NextCase = 1;
ProcessDone(TbProcNr_mem_cmd_c) <= '0';
work.psi_ms_daq_daq_dma_tb_case_unaligned.mem_cmd(Clk, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_mem_cmd_c) <= '1';
-- no_data_read
wait until NextCase = 2;
ProcessDone(TbProcNr_mem_cmd_c) <= '0';
work.psi_ms_daq_daq_dma_tb_case_no_data_read.mem_cmd(Clk, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_mem_cmd_c) <= '1';
-- input_empty
wait until NextCase = 3;
ProcessDone(TbProcNr_mem_cmd_c) <= '0';
work.psi_ms_daq_daq_dma_tb_case_input_empty.mem_cmd(Clk, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_mem_cmd_c) <= '1';
-- empty_timeout
wait until NextCase = 4;
ProcessDone(TbProcNr_mem_cmd_c) <= '0';
work.psi_ms_daq_daq_dma_tb_case_empty_timeout.mem_cmd(Clk, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_mem_cmd_c) <= '1';
-- cmd_full
wait until NextCase = 5;
ProcessDone(TbProcNr_mem_cmd_c) <= '0';
work.psi_ms_daq_daq_dma_tb_case_cmd_full.mem_cmd(Clk, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_mem_cmd_c) <= '1';
-- data_full
wait until NextCase = 6;
ProcessDone(TbProcNr_mem_cmd_c) <= '0';
work.psi_ms_daq_daq_dma_tb_case_data_full.mem_cmd(Clk, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_mem_cmd_c) <= '1';
-- errors
wait until NextCase = 7;
ProcessDone(TbProcNr_mem_cmd_c) <= '0';
work.psi_ms_daq_daq_dma_tb_case_errors.mem_cmd(Clk, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_mem_cmd_c) <= '1';
wait;
end process;
-- *** mem_dat ***
p_mem_dat : process
begin
-- aligned
wait until NextCase = 0;
ProcessDone(TbProcNr_mem_dat_c) <= '0';
work.psi_ms_daq_daq_dma_tb_case_aligned.mem_dat(Clk, Mem_DatData, Mem_DatVld, Mem_DatRdy, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_mem_dat_c) <= '1';
-- unaligned
wait until NextCase = 1;
ProcessDone(TbProcNr_mem_dat_c) <= '0';
work.psi_ms_daq_daq_dma_tb_case_unaligned.mem_dat(Clk, Mem_DatData, Mem_DatVld, Mem_DatRdy, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_mem_dat_c) <= '1';
-- no_data_read
wait until NextCase = 2;
ProcessDone(TbProcNr_mem_dat_c) <= '0';
work.psi_ms_daq_daq_dma_tb_case_no_data_read.mem_dat(Clk, Mem_DatData, Mem_DatVld, Mem_DatRdy, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_mem_dat_c) <= '1';
-- input_empty
wait until NextCase = 3;
ProcessDone(TbProcNr_mem_dat_c) <= '0';
work.psi_ms_daq_daq_dma_tb_case_input_empty.mem_dat(Clk, Mem_DatData, Mem_DatVld, Mem_DatRdy, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_mem_dat_c) <= '1';
-- empty_timeout
wait until NextCase = 4;
ProcessDone(TbProcNr_mem_dat_c) <= '0';
work.psi_ms_daq_daq_dma_tb_case_empty_timeout.mem_dat(Clk, Mem_DatData, Mem_DatVld, Mem_DatRdy, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_mem_dat_c) <= '1';
-- cmd_full
wait until NextCase = 5;
ProcessDone(TbProcNr_mem_dat_c) <= '0';
work.psi_ms_daq_daq_dma_tb_case_cmd_full.mem_dat(Clk, Mem_DatData, Mem_DatVld, Mem_DatRdy, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_mem_dat_c) <= '1';
-- data_full
wait until NextCase = 6;
ProcessDone(TbProcNr_mem_dat_c) <= '0';
work.psi_ms_daq_daq_dma_tb_case_data_full.mem_dat(Clk, Mem_DatData, Mem_DatVld, Mem_DatRdy, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_mem_dat_c) <= '1';
-- errors
wait until NextCase = 7;
ProcessDone(TbProcNr_mem_dat_c) <= '0';
work.psi_ms_daq_daq_dma_tb_case_errors.mem_dat(Clk, Mem_DatData, Mem_DatVld, Mem_DatRdy, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_mem_dat_c) <= '1';
wait;
end process;
end;

View File

@@ -1,173 +0,0 @@
------------------------------------------------------------
-- Libraries
------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_common_logic_pkg.all;
use work.psi_common_array_pkg.all;
use work.psi_ms_daq_pkg.all;
library work;
use work.psi_ms_daq_daq_dma_tb_pkg.all;
library work;
use work.psi_tb_txt_util.all;
use work.psi_tb_compare_pkg.all;
use work.psi_tb_activity_pkg.all;
------------------------------------------------------------
-- Package Header
------------------------------------------------------------
package psi_ms_daq_daq_dma_tb_case_aligned is
procedure control (
signal Clk : in std_logic;
signal Rst : inout std_logic;
signal DaqSm_Cmd : inout DaqSm2DaqDma_Cmd_t;
signal DaqSm_Cmd_Vld : inout std_logic;
signal DaqSm_Resp : in DaqDma2DaqSm_Resp_t;
signal DaqSm_Resp_Vld : in std_logic;
signal DaqSm_Resp_Rdy : inout std_logic;
signal DaqSm_HasLast : in std_logic_vector;
constant Generics_c : Generics_t);
procedure input (
signal Clk : in std_logic;
signal Inp_Vld : inout std_logic_vector;
signal Inp_Rdy : in std_logic_vector;
signal Inp_Data : inout Input2Daq_Data_a;
constant Generics_c : Generics_t);
procedure mem_cmd (
signal Clk : in std_logic;
signal Mem_CmdAddr : in std_logic_vector;
signal Mem_CmdSize : in std_logic_vector;
signal Mem_CmdVld : in std_logic;
signal Mem_CmdRdy : inout std_logic;
constant Generics_c : Generics_t);
procedure mem_dat (
signal Clk : in std_logic;
signal Mem_DatData : in std_logic_vector;
signal Mem_DatVld : in std_logic;
signal Mem_DatRdy : inout std_logic;
constant Generics_c : Generics_t);
end package;
------------------------------------------------------------
-- Package Body
------------------------------------------------------------
package body psi_ms_daq_daq_dma_tb_case_aligned is
procedure control (
signal Clk : in std_logic;
signal Rst : inout std_logic;
signal DaqSm_Cmd : inout DaqSm2DaqDma_Cmd_t;
signal DaqSm_Cmd_Vld : inout std_logic;
signal DaqSm_Resp : in DaqDma2DaqSm_Resp_t;
signal DaqSm_Resp_Vld : in std_logic;
signal DaqSm_Resp_Rdy : inout std_logic;
signal DaqSm_HasLast : in std_logic_vector;
constant Generics_c : Generics_t) is
begin
InitCase(Clk, Rst);
print(">> -- Aligned --");
-- Ready always high
print(">> Ready always high");
InitSubCase(0);
ApplyCmd(2, 16#01230000#, 32, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 32, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
WaitAllProc(Clk);
-- Data Ready toggling
print(">> Data Ready toggling");
InitSubCase(1);
ApplyCmd(2, 16#01231000#, 32, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 32, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
WaitAllProc(Clk);
-- Cmd Ready toggling
print(">> Cmd Ready toggling");
InitSubCase(2);
ApplyCmd(2, 16#01232000#, 32, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 32, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
WaitAllProc(Clk);
end procedure;
procedure input (
signal Clk : in std_logic;
signal Inp_Vld : inout std_logic_vector;
signal Inp_Rdy : in std_logic_vector;
signal Inp_Data : inout Input2Daq_Data_a;
constant Generics_c : Generics_t) is
begin
-- Ready always high
WaitForCase(0, Clk);
ApplyData(2, 32, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk);
ProcDone_V(0) := '1';
-- Data Ready toggling
WaitForCase(1, Clk);
ApplyData(2, 32, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk);
ProcDone_V(0) := '1';
-- Cmd Ready toggling
WaitForCase(2, Clk);
ApplyData(2, 32, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk);
ProcDone_V(0) := '1';
end procedure;
procedure mem_cmd (
signal Clk : in std_logic;
signal Mem_CmdAddr : in std_logic_vector;
signal Mem_CmdSize : in std_logic_vector;
signal Mem_CmdVld : in std_logic;
signal Mem_CmdRdy : inout std_logic;
constant Generics_c : Generics_t) is
begin
-- Ready always high
WaitForCase(0, Clk);
CheckMemCmd( 16#01230000#, 32, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
ProcDone_V(1) := '1';
-- Data Ready toggling
WaitForCase(1, Clk);
CheckMemCmd( 16#01231000#, 32, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
ProcDone_V(1) := '1';
-- Cmd Ready toggling
WaitForCase(2, Clk);
CheckMemCmd( 16#01232000#, 32, 5, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
ProcDone_V(1) := '1';
end procedure;
procedure mem_dat (
signal Clk : in std_logic;
signal Mem_DatData : in std_logic_vector;
signal Mem_DatVld : in std_logic;
signal Mem_DatRdy : inout std_logic;
constant Generics_c : Generics_t) is
begin
-- Ready always high
WaitForCase(0, Clk);
CheckMemData(32, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk);
ProcDone_V(2) := '1';
-- Data Ready toggling
WaitForCase(1, Clk);
CheckMemData(32, 5, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk);
ProcDone_V(2) := '1';
-- Ready always high
WaitForCase(2, Clk);
CheckMemData(32, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk);
ProcDone_V(2) := '1';
end procedure;
end;

View File

@@ -1,137 +0,0 @@
------------------------------------------------------------
-- Libraries
------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_common_logic_pkg.all;
use work.psi_common_array_pkg.all;
use work.psi_ms_daq_pkg.all;
library work;
use work.psi_ms_daq_daq_dma_tb_pkg.all;
library work;
use work.psi_tb_txt_util.all;
use work.psi_tb_compare_pkg.all;
use work.psi_tb_activity_pkg.all;
------------------------------------------------------------
-- Package Header
------------------------------------------------------------
package psi_ms_daq_daq_dma_tb_case_cmd_full is
procedure control (
signal Clk : in std_logic;
signal Rst : inout std_logic;
signal DaqSm_Cmd : inout DaqSm2DaqDma_Cmd_t;
signal DaqSm_Cmd_Vld : inout std_logic;
signal DaqSm_Resp : in DaqDma2DaqSm_Resp_t;
signal DaqSm_Resp_Vld : in std_logic;
signal DaqSm_Resp_Rdy : inout std_logic;
signal DaqSm_HasLast : in std_logic_vector;
constant Generics_c : Generics_t);
procedure input (
signal Clk : in std_logic;
signal Inp_Vld : inout std_logic_vector;
signal Inp_Rdy : in std_logic_vector;
signal Inp_Data : inout Input2Daq_Data_a;
constant Generics_c : Generics_t);
procedure mem_cmd (
signal Clk : in std_logic;
signal Mem_CmdAddr : in std_logic_vector;
signal Mem_CmdSize : in std_logic_vector;
signal Mem_CmdVld : in std_logic;
signal Mem_CmdRdy : inout std_logic;
constant Generics_c : Generics_t);
procedure mem_dat (
signal Clk : in std_logic;
signal Mem_DatData : in std_logic_vector;
signal Mem_DatVld : in std_logic;
signal Mem_DatRdy : inout std_logic;
constant Generics_c : Generics_t);
end package;
------------------------------------------------------------
-- Package Body
------------------------------------------------------------
package body psi_ms_daq_daq_dma_tb_case_cmd_full is
procedure control (
signal Clk : in std_logic;
signal Rst : inout std_logic;
signal DaqSm_Cmd : inout DaqSm2DaqDma_Cmd_t;
signal DaqSm_Cmd_Vld : inout std_logic;
signal DaqSm_Resp : in DaqDma2DaqSm_Resp_t;
signal DaqSm_Resp_Vld : in std_logic;
signal DaqSm_Resp_Rdy : inout std_logic;
signal DaqSm_HasLast : in std_logic_vector;
constant Generics_c : Generics_t) is
begin
InitCase(Clk, Rst);
print(">> -- Memory CMD full --");
-- Command not ready
wait for 1 us;
print(">> Command not ready");
InitCase(Clk, Rst);
InitSubCase(0);
ApplyCmd(2, 16#01230000#, 30, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 30, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
ApplyCmd(2, 16#01231000#, 30, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 30, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
end procedure;
procedure input (
signal Clk : in std_logic;
signal Inp_Vld : inout std_logic_vector;
signal Inp_Rdy : in std_logic_vector;
signal Inp_Data : inout Input2Daq_Data_a;
constant Generics_c : Generics_t) is
begin
-- Command not ready
WaitForCase(0, Clk);
ApplyData(2, 30, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk);
ApplyData(2, 30, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk, 30);
ProcDone_V(0) := '1';
end procedure;
procedure mem_cmd (
signal Clk : in std_logic;
signal Mem_CmdAddr : in std_logic_vector;
signal Mem_CmdSize : in std_logic_vector;
signal Mem_CmdVld : in std_logic;
signal Mem_CmdRdy : inout std_logic;
constant Generics_c : Generics_t) is
begin
-- Command not ready
WaitForCase(0, Clk);
Mem_CmdRdy <= '0';
wait until rising_edge(Clk) and Mem_CmdVld = '1';
CheckNoActivity(Mem_CmdVld, 2 us, 1, "Mem_CmdVld went high");
CheckMemCmd( 16#01230000#, 30, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
CheckMemCmd( 16#01231000#, 30, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
ProcDone_V(1) := '1';
end procedure;
procedure mem_dat (
signal Clk : in std_logic;
signal Mem_DatData : in std_logic_vector;
signal Mem_DatVld : in std_logic;
signal Mem_DatRdy : inout std_logic;
constant Generics_c : Generics_t) is
begin
-- Command not ready
WaitForCase(0, Clk);
CheckMemData(30, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 0, "1.0");
CheckMemData(30, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 30, "1.1");
ProcDone_V(2) := '1';
end procedure;
end;

View File

@@ -1,143 +0,0 @@
------------------------------------------------------------
-- Libraries
------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_common_logic_pkg.all;
use work.psi_common_array_pkg.all;
use work.psi_ms_daq_pkg.all;
library work;
use work.psi_ms_daq_daq_dma_tb_pkg.all;
library work;
use work.psi_tb_txt_util.all;
use work.psi_tb_compare_pkg.all;
use work.psi_tb_activity_pkg.all;
------------------------------------------------------------
-- Package Header
------------------------------------------------------------
package psi_ms_daq_daq_dma_tb_case_data_full is
procedure control (
signal Clk : in std_logic;
signal Rst : inout std_logic;
signal DaqSm_Cmd : inout DaqSm2DaqDma_Cmd_t;
signal DaqSm_Cmd_Vld : inout std_logic;
signal DaqSm_Resp : in DaqDma2DaqSm_Resp_t;
signal DaqSm_Resp_Vld : in std_logic;
signal DaqSm_Resp_Rdy : inout std_logic;
signal DaqSm_HasLast : in std_logic_vector;
constant Generics_c : Generics_t);
procedure input (
signal Clk : in std_logic;
signal Inp_Vld : inout std_logic_vector;
signal Inp_Rdy : in std_logic_vector;
signal Inp_Data : inout Input2Daq_Data_a;
constant Generics_c : Generics_t);
procedure mem_cmd (
signal Clk : in std_logic;
signal Mem_CmdAddr : in std_logic_vector;
signal Mem_CmdSize : in std_logic_vector;
signal Mem_CmdVld : in std_logic;
signal Mem_CmdRdy : inout std_logic;
constant Generics_c : Generics_t);
procedure mem_dat (
signal Clk : in std_logic;
signal Mem_DatData : in std_logic_vector;
signal Mem_DatVld : in std_logic;
signal Mem_DatRdy : inout std_logic;
constant Generics_c : Generics_t);
constant DataFifoDepth_c : integer := 64;
constant DataWidthBytes_c : integer := 8;
constant OversizeTfBytes_c : integer := DataFifoDepth_c*DataWidthBytes_c+12;
end package;
------------------------------------------------------------
-- Package Body
------------------------------------------------------------
package body psi_ms_daq_daq_dma_tb_case_data_full is
procedure control (
signal Clk : in std_logic;
signal Rst : inout std_logic;
signal DaqSm_Cmd : inout DaqSm2DaqDma_Cmd_t;
signal DaqSm_Cmd_Vld : inout std_logic;
signal DaqSm_Resp : in DaqDma2DaqSm_Resp_t;
signal DaqSm_Resp_Vld : in std_logic;
signal DaqSm_Resp_Rdy : inout std_logic;
signal DaqSm_HasLast : in std_logic_vector;
constant Generics_c : Generics_t) is
begin
InitCase(Clk, Rst);
print(">> -- Memory Data full --");
-- During Transfer
wait for 1 us;
print(">> During Transfer");
InitCase(Clk, Rst);
InitSubCase(0);
ApplyCmd(2, 16#01230000#, OversizeTfBytes_c, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, OversizeTfBytes_c, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
ApplyCmd(2, 16#01231000#, 30, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 30, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
end procedure;
procedure input (
signal Clk : in std_logic;
signal Inp_Vld : inout std_logic_vector;
signal Inp_Rdy : in std_logic_vector;
signal Inp_Data : inout Input2Daq_Data_a;
constant Generics_c : Generics_t) is
begin
-- During Transfer
WaitForCase(0, Clk);
ApplyData(2, OversizeTfBytes_c, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk);
ApplyData(2, 30, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk, 0);
ProcDone_V(0) := '1';
end procedure;
procedure mem_cmd (
signal Clk : in std_logic;
signal Mem_CmdAddr : in std_logic_vector;
signal Mem_CmdSize : in std_logic_vector;
signal Mem_CmdVld : in std_logic;
signal Mem_CmdRdy : inout std_logic;
constant Generics_c : Generics_t) is
begin
-- During Transfer
WaitForCase(0, Clk);
CheckMemCmd( 16#01230000#, OversizeTfBytes_c, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
CheckMemCmd( 16#01231000#, 30, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
ProcDone_V(1) := '1';
end procedure;
procedure mem_dat (
signal Clk : in std_logic;
signal Mem_DatData : in std_logic_vector;
signal Mem_DatVld : in std_logic;
signal Mem_DatRdy : inout std_logic;
constant Generics_c : Generics_t) is
begin
-- During Transfer
WaitForCase(0, Clk);
Mem_DatRdy <= '0';
wait until rising_edge(Clk) and Mem_DatVld = '1';
CheckNoActivity(Mem_DatVld, 2 us, 1, "Mem_CmdVld went low");
wait until rising_edge(Clk);
CheckMemData(OversizeTfBytes_c, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 0, "1.0");
CheckMemData(30, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 0, "1.1");
ProcDone_V(2) := '1';
end procedure;
end;

View File

@@ -1,172 +0,0 @@
------------------------------------------------------------
-- Libraries
------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_common_logic_pkg.all;
use work.psi_common_array_pkg.all;
use work.psi_ms_daq_pkg.all;
library work;
use work.psi_ms_daq_daq_dma_tb_pkg.all;
library work;
use work.psi_tb_txt_util.all;
use work.psi_tb_compare_pkg.all;
use work.psi_tb_activity_pkg.all;
------------------------------------------------------------
-- Package Header
------------------------------------------------------------
package psi_ms_daq_daq_dma_tb_case_empty_timeout is
procedure control (
signal Clk : in std_logic;
signal Rst : inout std_logic;
signal DaqSm_Cmd : inout DaqSm2DaqDma_Cmd_t;
signal DaqSm_Cmd_Vld : inout std_logic;
signal DaqSm_Resp : in DaqDma2DaqSm_Resp_t;
signal DaqSm_Resp_Vld : in std_logic;
signal DaqSm_Resp_Rdy : inout std_logic;
signal DaqSm_HasLast : in std_logic_vector;
constant Generics_c : Generics_t);
procedure input (
signal Clk : in std_logic;
signal Inp_Vld : inout std_logic_vector;
signal Inp_Rdy : in std_logic_vector;
signal Inp_Data : inout Input2Daq_Data_a;
constant Generics_c : Generics_t);
procedure mem_cmd (
signal Clk : in std_logic;
signal Mem_CmdAddr : in std_logic_vector;
signal Mem_CmdSize : in std_logic_vector;
signal Mem_CmdVld : in std_logic;
signal Mem_CmdRdy : inout std_logic;
constant Generics_c : Generics_t);
procedure mem_dat (
signal Clk : in std_logic;
signal Mem_DatData : in std_logic_vector;
signal Mem_DatVld : in std_logic;
signal Mem_DatRdy : inout std_logic;
constant Generics_c : Generics_t);
end package;
------------------------------------------------------------
-- Package Body
------------------------------------------------------------
package body psi_ms_daq_daq_dma_tb_case_empty_timeout is
procedure control (
signal Clk : in std_logic;
signal Rst : inout std_logic;
signal DaqSm_Cmd : inout DaqSm2DaqDma_Cmd_t;
signal DaqSm_Cmd_Vld : inout std_logic;
signal DaqSm_Resp : in DaqDma2DaqSm_Resp_t;
signal DaqSm_Resp_Vld : in std_logic;
signal DaqSm_Resp_Rdy : inout std_logic;
signal DaqSm_HasLast : in std_logic_vector;
constant Generics_c : Generics_t) is
begin
InitCase(Clk, Rst);
print(">> -- Empty Timeout Frame --");
-- Without Leftover data
wait for 1 us;
print(">> Without Leftover data");
InitCase(Clk, Rst);
InitSubCase(0);
ApplyCmd(2, 16#01230000#, 32, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 32, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
ApplyCmd(2, 16#01231000#, 32, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 0, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
ApplyCmd(2, 16#01232000#, 32, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 32, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
WaitAllProc(Clk);
-- With Leftover data
wait for 1 us;
print(">> With Leftover data");
InitCase(Clk, Rst);
InitSubCase(1);
ApplyCmd(2, 16#01230000#, 30, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 30, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
ApplyCmd(2, 16#01231000#, 32, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 2, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
ApplyCmd(2, 16#01232000#, 32, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 32, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
WaitAllProc(Clk);
end procedure;
procedure input (
signal Clk : in std_logic;
signal Inp_Vld : inout std_logic_vector;
signal Inp_Rdy : in std_logic_vector;
signal Inp_Data : inout Input2Daq_Data_a;
constant Generics_c : Generics_t) is
begin
-- Without Leftover data
WaitForCase(0, Clk);
ApplyData(2, 32, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk);
ApplyData(2, 0, Timeout_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk);
ApplyData(2, 32, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk, 32);
ProcDone_V(0) := '1';
-- With Leftover data
WaitForCase(1, Clk);
ApplyData(2, 32, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk);
ApplyData(2, 0, Timeout_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk);
ApplyData(2, 32, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk, 32);
ProcDone_V(0) := '1';
end procedure;
procedure mem_cmd (
signal Clk : in std_logic;
signal Mem_CmdAddr : in std_logic_vector;
signal Mem_CmdSize : in std_logic_vector;
signal Mem_CmdVld : in std_logic;
signal Mem_CmdRdy : inout std_logic;
constant Generics_c : Generics_t) is
begin
-- Without Leftover data
WaitForCase(0, Clk);
CheckMemCmd( 16#01230000#, 32, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
CheckMemCmd( 16#01232000#, 32, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
ProcDone_V(1) := '1';
-- With Leftover data
WaitForCase(1, Clk);
CheckMemCmd( 16#01230000#, 30, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
CheckMemCmd( 16#01231000#, 2, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
CheckMemCmd( 16#01232000#, 32, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
ProcDone_V(1) := '1';
end procedure;
procedure mem_dat (
signal Clk : in std_logic;
signal Mem_DatData : in std_logic_vector;
signal Mem_DatVld : in std_logic;
signal Mem_DatRdy : inout std_logic;
constant Generics_c : Generics_t) is
begin
-- Without Leftover data
WaitForCase(0, Clk);
CheckMemData(32, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 0, "1.0");
CheckMemData(32, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 32, "1.2");
ProcDone_V(2) := '1';
-- With Leftover data
WaitForCase(1, Clk);
CheckMemData(30, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 0, "1.0");
CheckMemData(2, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 30, "1.1");
CheckMemData(32, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 32, "1.2");
ProcDone_V(2) := '1';
end procedure;
end;

View File

@@ -1,184 +0,0 @@
------------------------------------------------------------
-- Libraries
------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_common_logic_pkg.all;
use work.psi_common_array_pkg.all;
use work.psi_ms_daq_pkg.all;
library work;
use work.psi_ms_daq_daq_dma_tb_pkg.all;
library work;
use work.psi_tb_txt_util.all;
use work.psi_tb_compare_pkg.all;
use work.psi_tb_activity_pkg.all;
------------------------------------------------------------
-- Package Header
------------------------------------------------------------
package psi_ms_daq_daq_dma_tb_case_errors is
procedure control (
signal Clk : in std_logic;
signal Rst : inout std_logic;
signal DaqSm_Cmd : inout DaqSm2DaqDma_Cmd_t;
signal DaqSm_Cmd_Vld : inout std_logic;
signal DaqSm_Resp : in DaqDma2DaqSm_Resp_t;
signal DaqSm_Resp_Vld : in std_logic;
signal DaqSm_Resp_Rdy : inout std_logic;
signal DaqSm_HasLast : in std_logic_vector;
constant Generics_c : Generics_t);
procedure input (
signal Clk : in std_logic;
signal Inp_Vld : inout std_logic_vector;
signal Inp_Rdy : in std_logic_vector;
signal Inp_Data : inout Input2Daq_Data_a;
constant Generics_c : Generics_t);
procedure mem_cmd (
signal Clk : in std_logic;
signal Mem_CmdAddr : in std_logic_vector;
signal Mem_CmdSize : in std_logic_vector;
signal Mem_CmdVld : in std_logic;
signal Mem_CmdRdy : inout std_logic;
constant Generics_c : Generics_t);
procedure mem_dat (
signal Clk : in std_logic;
signal Mem_DatData : in std_logic_vector;
signal Mem_DatVld : in std_logic;
signal Mem_DatRdy : inout std_logic;
constant Generics_c : Generics_t);
end package;
------------------------------------------------------------
-- Package Body
------------------------------------------------------------
package body psi_ms_daq_daq_dma_tb_case_errors is
procedure control (
signal Clk : in std_logic;
signal Rst : inout std_logic;
signal DaqSm_Cmd : inout DaqSm2DaqDma_Cmd_t;
signal DaqSm_Cmd_Vld : inout std_logic;
signal DaqSm_Resp : in DaqDma2DaqSm_Resp_t;
signal DaqSm_Resp_Vld : in std_logic;
signal DaqSm_Resp_Rdy : inout std_logic;
signal DaqSm_HasLast : in std_logic_vector;
constant Generics_c : Generics_t) is
begin
InitCase(Clk, Rst);
print(">> -- Error cases from top-tb and HW --");
-- Trigger in remaining data
wait for 1 us;
print(">> Trigger in remaining data");
InitCase(Clk, Rst);
InitSubCase(0);
ApplyCmd(2, 16#01230000#, 26, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
StdlCompare(0, DaqSm_HasLast(2), "HasLast high unexpectedly");
CheckResp(2, 26, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
StdlCompare(1, DaqSm_HasLast(2), "HasLast low after incomplete frame");
ApplyCmd(2, 16#01231000#, 30, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
StdlCompare(1, DaqSm_HasLast(2), "HasLast low after completion command");
CheckResp(2, 2, Trigger_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
StdlCompare(0, DaqSm_HasLast(2), "HasLast high after completion response");
ApplyCmd(2, 16#01232000#, 30, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 30, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
WaitAllProc(Clk);
-- Timeout in remaining data
wait for 1 us;
print(">> Timeout in remaining data");
InitCase(Clk, Rst);
InitSubCase(1);
ApplyCmd(2, 16#01230000#, 26, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
StdlCompare(0, DaqSm_HasLast(2), "HasLast high unexpectedly");
CheckResp(2, 26, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
StdlCompare(1, DaqSm_HasLast(2), "HasLast low after incomplete frame");
ApplyCmd(2, 16#01231000#, 30, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
StdlCompare(1, DaqSm_HasLast(2), "HasLast low after completion command");
CheckResp(2, 2, Timeout_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
StdlCompare(0, DaqSm_HasLast(2), "HasLast high after completion response");
ApplyCmd(2, 16#01232000#, 30, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 30, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
WaitAllProc(Clk);
end procedure;
procedure input (
signal Clk : in std_logic;
signal Inp_Vld : inout std_logic_vector;
signal Inp_Rdy : in std_logic_vector;
signal Inp_Data : inout Input2Daq_Data_a;
constant Generics_c : Generics_t) is
begin
-- Trigger in remaining data
WaitForCase(0, Clk);
ApplyData(2, 28, Trigger_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk);
ApplyData(2, 30, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk, 128);
ProcDone_V(0) := '1';
-- Timeout in remaining data
WaitForCase(1, Clk);
ApplyData(2, 28, Timeout_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk);
ApplyData(2, 30, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk, 128);
ProcDone_V(0) := '1';
end procedure;
procedure mem_cmd (
signal Clk : in std_logic;
signal Mem_CmdAddr : in std_logic_vector;
signal Mem_CmdSize : in std_logic_vector;
signal Mem_CmdVld : in std_logic;
signal Mem_CmdRdy : inout std_logic;
constant Generics_c : Generics_t) is
begin
-- Trigger in remaining data
WaitForCase(0, Clk);
CheckMemCmd( 16#01230000#, 26, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
CheckMemCmd( 16#01231000#, 2, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
CheckMemCmd( 16#01232000#, 30, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
ProcDone_V(1) := '1';
-- Timeout in remaining data
WaitForCase(1, Clk);
CheckMemCmd( 16#01230000#, 26, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
CheckMemCmd( 16#01231000#, 2, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
CheckMemCmd( 16#01232000#, 30, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
ProcDone_V(1) := '1';
end procedure;
procedure mem_dat (
signal Clk : in std_logic;
signal Mem_DatData : in std_logic_vector;
signal Mem_DatVld : in std_logic;
signal Mem_DatRdy : inout std_logic;
constant Generics_c : Generics_t) is
begin
-- Trigger in remaining data
WaitForCase(0, Clk);
CheckMemData(26, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 0, "1.0");
CheckMemData(2, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 26, "1.1");
CheckMemData(30, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 128, "1.2");
ProcDone_V(2) := '1';
-- Timeout in remaining data
WaitForCase(1, Clk);
CheckMemData(26, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 0, "1.0");
CheckMemData(2, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 26, "1.1");
CheckMemData(30, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 128, "1.2");
ProcDone_V(2) := '1';
end procedure;
end;

View File

@@ -1,180 +0,0 @@
------------------------------------------------------------
-- Libraries
------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_common_logic_pkg.all;
use work.psi_common_array_pkg.all;
use work.psi_ms_daq_pkg.all;
library work;
use work.psi_ms_daq_daq_dma_tb_pkg.all;
library work;
use work.psi_tb_txt_util.all;
use work.psi_tb_compare_pkg.all;
use work.psi_tb_activity_pkg.all;
------------------------------------------------------------
-- Package Header
------------------------------------------------------------
package psi_ms_daq_daq_dma_tb_case_input_empty is
procedure control (
signal Clk : in std_logic;
signal Rst : inout std_logic;
signal DaqSm_Cmd : inout DaqSm2DaqDma_Cmd_t;
signal DaqSm_Cmd_Vld : inout std_logic;
signal DaqSm_Resp : in DaqDma2DaqSm_Resp_t;
signal DaqSm_Resp_Vld : in std_logic;
signal DaqSm_Resp_Rdy : inout std_logic;
signal DaqSm_HasLast : in std_logic_vector;
constant Generics_c : Generics_t);
procedure input (
signal Clk : in std_logic;
signal Inp_Vld : inout std_logic_vector;
signal Inp_Rdy : in std_logic_vector;
signal Inp_Data : inout Input2Daq_Data_a;
constant Generics_c : Generics_t);
procedure mem_cmd (
signal Clk : in std_logic;
signal Mem_CmdAddr : in std_logic_vector;
signal Mem_CmdSize : in std_logic_vector;
signal Mem_CmdVld : in std_logic;
signal Mem_CmdRdy : inout std_logic;
constant Generics_c : Generics_t);
procedure mem_dat (
signal Clk : in std_logic;
signal Mem_DatData : in std_logic_vector;
signal Mem_DatVld : in std_logic;
signal Mem_DatRdy : inout std_logic;
constant Generics_c : Generics_t);
shared variable SubCase : integer := 0;
end package;
------------------------------------------------------------
-- Package Body
------------------------------------------------------------
package body psi_ms_daq_daq_dma_tb_case_input_empty is
procedure control (
signal Clk : in std_logic;
signal Rst : inout std_logic;
signal DaqSm_Cmd : inout DaqSm2DaqDma_Cmd_t;
signal DaqSm_Cmd_Vld : inout std_logic;
signal DaqSm_Resp : in DaqDma2DaqSm_Resp_t;
signal DaqSm_Resp_Vld : in std_logic;
signal DaqSm_Resp_Rdy : inout std_logic;
signal DaqSm_HasLast : in std_logic_vector;
constant Generics_c : Generics_t) is
begin
InitCase(Clk, Rst);
print(">> -- Input Empty --");
-- Transfer aborted by input FIFO empty
wait for 1 us;
print(">> Transfer aborted by input FIFO empty");
InitCase(Clk, Rst);
InitSubCase(0);
ApplyCmd(2, 16#01230000#, 30, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 16, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
SubCase := 1;
ApplyCmd(2, 16#01231000#, 30, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 30, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
WaitAllProc(Clk);
-- With leftover data
wait for 1 us;
print(">> With leftover data");
InitCase(Clk, Rst);
InitSubCase(1);
ApplyCmd(2, 16#01230000#, 30, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 30, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
SubCase := 1;
ApplyCmd(2, 16#01231000#, 30, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 18, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
SubCase := 2;
ApplyCmd(2, 16#01232000#, 30, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 30, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
WaitAllProc(Clk);
end procedure;
procedure input (
signal Clk : in std_logic;
signal Inp_Vld : inout std_logic_vector;
signal Inp_Rdy : in std_logic_vector;
signal Inp_Data : inout Input2Daq_Data_a;
constant Generics_c : Generics_t) is
begin
-- Transfer aborted by input FIFO empty
WaitForCase(0, Clk);
ApplyData(2, 16, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk);
while SubCase < 1 loop
wait until rising_edge(Clk);
end loop;
ApplyData(2, 30, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk, 16);
ProcDone_V(0) := '1';
-- With leftover data
WaitForCase(1, Clk);
ApplyData(2, 48, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk);
while SubCase < 2 loop
wait until rising_edge(Clk);
end loop;
ApplyData(2, 30, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk, 48);
ProcDone_V(0) := '1';
end procedure;
procedure mem_cmd (
signal Clk : in std_logic;
signal Mem_CmdAddr : in std_logic_vector;
signal Mem_CmdSize : in std_logic_vector;
signal Mem_CmdVld : in std_logic;
signal Mem_CmdRdy : inout std_logic;
constant Generics_c : Generics_t) is
begin
-- Transfer aborted by input FIFO empty
WaitForCase(0, Clk);
CheckMemCmd( 16#01230000#, 16, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
CheckMemCmd( 16#01231000#, 30, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
ProcDone_V(1) := '1';
-- With leftover data
WaitForCase(1, Clk);
CheckMemCmd( 16#01230000#, 30, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
CheckMemCmd( 16#01231000#, 18, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
CheckMemCmd( 16#01232000#, 30, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
ProcDone_V(1) := '1';
end procedure;
procedure mem_dat (
signal Clk : in std_logic;
signal Mem_DatData : in std_logic_vector;
signal Mem_DatVld : in std_logic;
signal Mem_DatRdy : inout std_logic;
constant Generics_c : Generics_t) is
begin
-- Transfer aborted by input FIFO empty
WaitForCase(0, Clk);
CheckMemData(16, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 0, "1.0");
CheckMemData(30, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 16, "1.1");
ProcDone_V(2) := '1';
-- Transfer aborted by input FIFO empty
WaitForCase(1, Clk);
CheckMemData(30, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 0, "1.0");
CheckMemData(18, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 30, "1.1");
CheckMemData(30, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 30+18, "1.2");
ProcDone_V(2) := '1';
end procedure;
end;

View File

@@ -1,229 +0,0 @@
------------------------------------------------------------
-- Libraries
------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_common_logic_pkg.all;
use work.psi_common_array_pkg.all;
use work.psi_ms_daq_pkg.all;
library work;
use work.psi_ms_daq_daq_dma_tb_pkg.all;
library work;
use work.psi_tb_txt_util.all;
use work.psi_tb_compare_pkg.all;
use work.psi_tb_activity_pkg.all;
------------------------------------------------------------
-- Package Header
------------------------------------------------------------
package psi_ms_daq_daq_dma_tb_case_no_data_read is
procedure control (
signal Clk : in std_logic;
signal Rst : inout std_logic;
signal DaqSm_Cmd : inout DaqSm2DaqDma_Cmd_t;
signal DaqSm_Cmd_Vld : inout std_logic;
signal DaqSm_Resp : in DaqDma2DaqSm_Resp_t;
signal DaqSm_Resp_Vld : in std_logic;
signal DaqSm_Resp_Rdy : inout std_logic;
signal DaqSm_HasLast : in std_logic_vector;
constant Generics_c : Generics_t);
procedure input (
signal Clk : in std_logic;
signal Inp_Vld : inout std_logic_vector;
signal Inp_Rdy : in std_logic_vector;
signal Inp_Data : inout Input2Daq_Data_a;
constant Generics_c : Generics_t);
procedure mem_cmd (
signal Clk : in std_logic;
signal Mem_CmdAddr : in std_logic_vector;
signal Mem_CmdSize : in std_logic_vector;
signal Mem_CmdVld : in std_logic;
signal Mem_CmdRdy : inout std_logic;
constant Generics_c : Generics_t);
procedure mem_dat (
signal Clk : in std_logic;
signal Mem_DatData : in std_logic_vector;
signal Mem_DatVld : in std_logic;
signal Mem_DatRdy : inout std_logic;
constant Generics_c : Generics_t);
shared variable SubCase : integer := 0;
end package;
------------------------------------------------------------
-- Package Body
------------------------------------------------------------
package body psi_ms_daq_daq_dma_tb_case_no_data_read is
procedure control (
signal Clk : in std_logic;
signal Rst : inout std_logic;
signal DaqSm_Cmd : inout DaqSm2DaqDma_Cmd_t;
signal DaqSm_Cmd_Vld : inout std_logic;
signal DaqSm_Resp : in DaqDma2DaqSm_Resp_t;
signal DaqSm_Resp_Vld : in std_logic;
signal DaqSm_Resp_Rdy : inout std_logic;
signal DaqSm_HasLast : in std_logic_vector;
constant Generics_c : Generics_t) is
begin
InitCase(Clk, Rst);
print(">> -- No data read --");
-- No Data on first request
print(">> No Data on first request");
InitCase(Clk, Rst);
InitSubCase(0);
ApplyCmd(2, 16#01230000#, 30, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 0, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
SubCase := 1;
ApplyCmd(2, 16#01231000#, 30, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 30, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
WaitAllProc(Clk);
SubCase := 0;
-- No Data on second request
wait for 1 us;
print(">> No Data on second request");
InitCase(Clk, Rst);
InitSubCase(1);
ApplyCmd(2, 16#01230000#, 32, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 32, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
ApplyCmd(2, 16#01231000#, 30, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 0, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
SubCase := 1;
ApplyCmd(2, 16#01232000#, 30, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 30, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
WaitAllProc(Clk);
SubCase := 0;
-- No Data with leftover bytes
wait for 1 us;
print(">> No Data with leftover bytes");
InitCase(Clk, Rst);
InitSubCase(2);
ApplyCmd(2, 16#01230000#, 30, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 30, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
ApplyCmd(2, 16#01231000#, 30, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 2, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
SubCase := 1;
ApplyCmd(2, 16#01232000#, 30, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 30, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
WaitAllProc(Clk);
SubCase := 0;
end procedure;
procedure input (
signal Clk : in std_logic;
signal Inp_Vld : inout std_logic_vector;
signal Inp_Rdy : in std_logic_vector;
signal Inp_Data : inout Input2Daq_Data_a;
constant Generics_c : Generics_t) is
begin
-- No Data on first request
WaitForCase(0, Clk);
while SubCase < 1 loop
wait until rising_edge(Clk);
end loop;
ApplyData(2, 30, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk);
ProcDone_V(0) := '1';
-- No Data on second request
WaitForCase(1, Clk);
ApplyData(2, 32, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk);
while SubCase < 1 loop
wait until rising_edge(Clk);
end loop;
ApplyData(2, 30, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk, 32);
ProcDone_V(0) := '1';
-- No Data with leftover bytes
WaitForCase(2, Clk);
ApplyData(2, 32, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk);
while SubCase < 1 loop
wait until rising_edge(Clk);
end loop;
ApplyData(2, 30, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk, 32);
ProcDone_V(0) := '1';
end procedure;
procedure mem_cmd (
signal Clk : in std_logic;
signal Mem_CmdAddr : in std_logic_vector;
signal Mem_CmdSize : in std_logic_vector;
signal Mem_CmdVld : in std_logic;
signal Mem_CmdRdy : inout std_logic;
constant Generics_c : Generics_t) is
begin
-- No Data on first request
WaitForCase(0, Clk);
while SubCase < 1 loop
StdlCompare(0, Mem_CmdVld, "Unexpected memory command");
wait until rising_edge(Clk);
end loop;
CheckMemCmd( 16#01231000#, 30, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
ProcDone_V(1) := '1';
-- No Data on second request
WaitForCase(1, Clk);
CheckMemCmd( 16#01230000#, 32, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
while SubCase < 1 loop
StdlCompare(0, Mem_CmdVld, "Unexpected memory command");
wait until rising_edge(Clk);
end loop;
CheckMemCmd( 16#01232000#, 30, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
ProcDone_V(1) := '1';
-- No Data with leftover bytes
WaitForCase(2, Clk);
CheckMemCmd( 16#01230000#, 30, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
CheckMemCmd( 16#01231000#, 2, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
CheckMemCmd( 16#01232000#, 30, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
ProcDone_V(1) := '1';
end procedure;
procedure mem_dat (
signal Clk : in std_logic;
signal Mem_DatData : in std_logic_vector;
signal Mem_DatVld : in std_logic;
signal Mem_DatRdy : inout std_logic;
constant Generics_c : Generics_t) is
begin
-- No Data on first request
WaitForCase(0, Clk);
while SubCase < 1 loop
wait until rising_edge(Clk);
StdlCompare(0, Mem_DatVld, "Unexpected memory data");
end loop;
CheckMemData(30, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 0, "1.1");
ProcDone_V(2) := '1';
-- No Data on second request
WaitForCase(1, Clk);
CheckMemData(32, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 0, "1.0");
while SubCase < 1 loop
wait until rising_edge(Clk);
StdlCompare(0, Mem_DatVld, "Unexpected memory data");
end loop;
CheckMemData(30, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 32, "1.2");
ProcDone_V(2) := '1';
-- No Data with leftover bytes
WaitForCase(2, Clk);
CheckMemData(30, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 0, "1.0");
CheckMemData(2, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 30, "1.1");
CheckMemData(30, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 30+2, "1.2");
ProcDone_V(2) := '1';
end procedure;
end;

View File

@@ -1,378 +0,0 @@
------------------------------------------------------------
-- Libraries
------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_common_logic_pkg.all;
use work.psi_common_array_pkg.all;
use work.psi_ms_daq_pkg.all;
library work;
use work.psi_ms_daq_daq_dma_tb_pkg.all;
library work;
use work.psi_tb_txt_util.all;
use work.psi_tb_compare_pkg.all;
use work.psi_tb_activity_pkg.all;
------------------------------------------------------------
-- Package Header
------------------------------------------------------------
package psi_ms_daq_daq_dma_tb_case_unaligned is
procedure control (
signal Clk : in std_logic;
signal Rst : inout std_logic;
signal DaqSm_Cmd : inout DaqSm2DaqDma_Cmd_t;
signal DaqSm_Cmd_Vld : inout std_logic;
signal DaqSm_Resp : in DaqDma2DaqSm_Resp_t;
signal DaqSm_Resp_Vld : in std_logic;
signal DaqSm_Resp_Rdy : inout std_logic;
signal DaqSm_HasLast : in std_logic_vector;
constant Generics_c : Generics_t);
procedure input (
signal Clk : in std_logic;
signal Inp_Vld : inout std_logic_vector;
signal Inp_Rdy : in std_logic_vector;
signal Inp_Data : inout Input2Daq_Data_a;
constant Generics_c : Generics_t);
procedure mem_cmd (
signal Clk : in std_logic;
signal Mem_CmdAddr : in std_logic_vector;
signal Mem_CmdSize : in std_logic_vector;
signal Mem_CmdVld : in std_logic;
signal Mem_CmdRdy : inout std_logic;
constant Generics_c : Generics_t);
procedure mem_dat (
signal Clk : in std_logic;
signal Mem_DatData : in std_logic_vector;
signal Mem_DatVld : in std_logic;
signal Mem_DatRdy : inout std_logic;
constant Generics_c : Generics_t);
end package;
------------------------------------------------------------
-- Package Body
------------------------------------------------------------
package body psi_ms_daq_daq_dma_tb_case_unaligned is
procedure control (
signal Clk : in std_logic;
signal Rst : inout std_logic;
signal DaqSm_Cmd : inout DaqSm2DaqDma_Cmd_t;
signal DaqSm_Cmd_Vld : inout std_logic;
signal DaqSm_Resp : in DaqDma2DaqSm_Resp_t;
signal DaqSm_Resp_Vld : in std_logic;
signal DaqSm_Resp_Rdy : inout std_logic;
signal DaqSm_HasLast : in std_logic_vector;
constant Generics_c : Generics_t) is
begin
InitCase(Clk, Rst);
print(">> -- Unaligned --");
-- End Unaligned
print(">> End Unaligned");
InitCase(Clk, Rst);
InitSubCase(0);
ApplyCmd(2, 16#01230000#, 30, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 30, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
ApplyCmd(2, 16#01231000#, 29, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 29, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
ApplyCmd(2, 16#01232000#, 30, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 30, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
WaitAllProc(Clk);
-- QWord Split
print(">> QWord Split");
InitCase(Clk, Rst);
InitSubCase(1);
ApplyCmd(2, 16#01230000#, 30, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 30, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
ApplyCmd(2, 16#01231000#, 29, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 29, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
ApplyCmd(2, 16#01232000#, 30, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 30, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
WaitAllProc(Clk);
-- QWord Split, Rdy Toggling
print(">> QWord Split, Rdy Toggling");
InitCase(Clk, Rst);
InitSubCase(2);
ApplyCmd(2, 16#01230000#, 30, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 30, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
ApplyCmd(2, 16#01231000#, 29, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 29, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
ApplyCmd(2, 16#01232000#, 30, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 30, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
WaitAllProc(Clk);
-- mixed streams
print(">> mixed streams");
InitCase(Clk, Rst);
InitSubCase(3);
ApplyCmd(2, 16#02000000#, 30, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
ApplyCmd(1, 16#01000000#, 23, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 30, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
CheckResp(1, 23, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
ApplyCmd(2, 16#02000001#, 33, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
ApplyCmd(1, 16#01000001#, 21, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 33, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
CheckResp(1, 21, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
ApplyCmd(1, 16#01000002#, 11, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
ApplyCmd(2, 16#02000002#, 11, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(1, 11, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
CheckResp(2, 11, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
WaitAllProc(Clk);
-- End Aligned
print(">> End Aligned");
InitCase(Clk, Rst);
InitSubCase(4);
ApplyCmd(2, 16#01230000#, 30, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 30, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
ApplyCmd(2, 16#01231000#, 34, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 34, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
ApplyCmd(2, 16#01232000#, 30, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 30, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
WaitAllProc(Clk);
-- Unaligned end by trigger (with rem-word)
print(">> Unaligned end by trigger (with rem-word)");
InitCase(Clk, Rst);
InitSubCase(5);
ApplyCmd(2, 16#01230000#, 30, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 30, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
ApplyCmd(2, 16#01231000#, 64, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 29, Trigger_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
ApplyCmd(2, 16#01232000#, 30, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 30, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
WaitAllProc(Clk);
-- Unaligned end by trigger (without rem-word)
print(">> Unaligned end by trigger (without rem-word)");
InitCase(Clk, Rst);
InitSubCase(6);
ApplyCmd(2, 16#01230000#, 30, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 30, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
ApplyCmd(2, 16#01231000#, 64, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 25, Trigger_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
ApplyCmd(2, 16#01232000#, 30, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 30, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
WaitAllProc(Clk);
-- Unaligned end by timeout
print(">> Unaligned end by timeout");
InitCase(Clk, Rst);
InitSubCase(7);
ApplyCmd(2, 16#01230000#, 30, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 30, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
ApplyCmd(2, 16#01231000#, 64, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 29, Timeout_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
ApplyCmd(2, 16#01232000#, 30, DaqSm_Cmd, DaqSm_Cmd_Vld, Clk);
CheckResp(2, 30, NoEnd_s, DaqSm_Resp, DaqSm_Resp_Vld, DaqSm_Resp_Rdy, Clk);
WaitAllProc(Clk);
end procedure;
procedure input (
signal Clk : in std_logic;
signal Inp_Vld : inout std_logic_vector;
signal Inp_Rdy : in std_logic_vector;
signal Inp_Data : inout Input2Daq_Data_a;
constant Generics_c : Generics_t) is
begin
-- End Unaligned
WaitForCase(0, Clk);
ApplyData(2, 30, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk);
ApplyData(2, 29, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk, 30);
ApplyData(2, 30, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk, 30+29);
ProcDone_V(0) := '1';
-- QWord Split
WaitForCase(1, Clk);
ApplyData(2, 30+29+30, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk);
ProcDone_V(0) := '1';
-- QWord Split, Rdy Toggling
WaitForCase(2, Clk);
ApplyData(2, 30+29+30, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk);
ProcDone_V(0) := '1';
-- mixed streams
WaitForCase(3, Clk);
ApplyData(2, 32, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk);
ApplyData(1, 24, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk);
ApplyData(2, 32, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk, 32);
ApplyData(1, 20, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk, 24);
ApplyData(1, 12, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk, 20+24);
ApplyData(2, 12, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk, 32+32);
ProcDone_V(0) := '1';
-- End Aligned
WaitForCase(4, Clk);
ApplyData(2, 30+34+30, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk);
ProcDone_V(0) := '1';
-- Unaligned end by trigger (with rem-word)
WaitForCase(5, Clk);
ApplyData(2, 30+29, Trigger_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk, 0);
ApplyData(2, 30, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk, 30+29);
ProcDone_V(0) := '1';
-- Unaligned end by trigger (without rem-word)
WaitForCase(6, Clk);
ApplyData(2, 30+25, Trigger_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk, 0);
ApplyData(2, 30, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk, 30+25);
ProcDone_V(0) := '1';
-- Unaligned end by timeout
WaitForCase(7, Clk);
ApplyData(2, 30+29, Timeout_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk, 0);
ApplyData(2, 30, NoEnd_s, Inp_Vld, Inp_Rdy, Inp_Data, Clk, 30+29);
ProcDone_V(0) := '1';
end procedure;
procedure mem_cmd (
signal Clk : in std_logic;
signal Mem_CmdAddr : in std_logic_vector;
signal Mem_CmdSize : in std_logic_vector;
signal Mem_CmdVld : in std_logic;
signal Mem_CmdRdy : inout std_logic;
constant Generics_c : Generics_t) is
begin
-- End Unaligned
WaitForCase(0, Clk);
CheckMemCmd( 16#01230000#, 30, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
CheckMemCmd( 16#01231000#, 29, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
CheckMemCmd( 16#01232000#, 30, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
ProcDone_V(1) := '1';
-- QWord Split
WaitForCase(1, Clk);
CheckMemCmd( 16#01230000#, 30, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
CheckMemCmd( 16#01231000#, 29, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
CheckMemCmd( 16#01232000#, 30, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
ProcDone_V(1) := '1';
-- QWord Split, Rdy Toggling
WaitForCase(2, Clk);
CheckMemCmd( 16#01230000#, 30, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
CheckMemCmd( 16#01231000#, 29, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
CheckMemCmd( 16#01232000#, 30, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
ProcDone_V(1) := '1';
-- mixed streams
WaitForCase(3, Clk);
CheckMemCmd( 16#02000000#, 30, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk, "2.0");
CheckMemCmd( 16#01000000#, 23, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk, "1.0");
CheckMemCmd( 16#02000001#, 33, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk, "2.1");
CheckMemCmd( 16#01000001#, 21, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk, "1.1");
CheckMemCmd( 16#01000002#, 11, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk, "1.2");
CheckMemCmd( 16#02000002#, 11, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk, "2.2");
ProcDone_V(1) := '1';
-- End Aligned
WaitForCase(4, Clk);
CheckMemCmd( 16#01230000#, 30, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
CheckMemCmd( 16#01231000#, 34, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
CheckMemCmd( 16#01232000#, 30, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
ProcDone_V(1) := '1';
-- Unaligned end by trigger (with rem-word)
WaitForCase(5, Clk);
CheckMemCmd( 16#01230000#, 30, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
CheckMemCmd( 16#01231000#, 29, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
CheckMemCmd( 16#01232000#, 30, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
ProcDone_V(1) := '1';
-- Unaligned end by trigger (without rem-word)
WaitForCase(6, Clk);
CheckMemCmd( 16#01230000#, 30, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
CheckMemCmd( 16#01231000#, 25, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
CheckMemCmd( 16#01232000#, 30, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
ProcDone_V(1) := '1';
-- Unaligned end by timeout
WaitForCase(7, Clk);
CheckMemCmd( 16#01230000#, 30, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
CheckMemCmd( 16#01231000#, 29, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
CheckMemCmd( 16#01232000#, 30, 0, Mem_CmdAddr, Mem_CmdSize, Mem_CmdVld, Mem_CmdRdy, Clk);
ProcDone_V(1) := '1';
end procedure;
procedure mem_dat (
signal Clk : in std_logic;
signal Mem_DatData : in std_logic_vector;
signal Mem_DatVld : in std_logic;
signal Mem_DatRdy : inout std_logic;
constant Generics_c : Generics_t) is
begin
-- End Unaligned
WaitForCase(0, Clk);
CheckMemData(30, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 0, "1.0");
CheckMemData(29, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 30, "1.1");
CheckMemData(30, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 30+29, "1.2");
ProcDone_V(2) := '1';
-- QWord Split
WaitForCase(1, Clk);
CheckMemData(30, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk);
CheckMemData(29, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 30);
CheckMemData(30, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 30+29);
ProcDone_V(2) := '1';
-- QWord Split, Rdy Toggling
WaitForCase(2, Clk);
CheckMemData(30, 5, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk);
CheckMemData(29, 5, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 30);
CheckMemData(30, 5, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 30+29);
ProcDone_V(2) := '1';
-- mixed streams
WaitForCase(3, Clk);
CheckMemData(30, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 0, "2.0");
CheckMemData(23, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 0, "1.0");
CheckMemData(33, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 30, "2.1");
CheckMemData(21, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 23, "1.1");
CheckMemData(11, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 23+21, "1.2");
CheckMemData(11, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 30+33, "2.2");
ProcDone_V(2) := '1';
-- End Unaligned
WaitForCase(4, Clk);
CheckMemData(30, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 0, "1.0");
CheckMemData(34, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 30, "1.1");
CheckMemData(30, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 30+34, "1.2");
ProcDone_V(2) := '1';
-- Unaligned end by trigger (with rem-word)
WaitForCase(5, Clk);
CheckMemData(30, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 0, "1.0");
CheckMemData(29, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 30, "1.1");
CheckMemData(30, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 30+29, "1.2");
ProcDone_V(2) := '1';
-- Unaligned end by trigger (without rem-word)
WaitForCase(6, Clk);
CheckMemData(30, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 0, "1.0");
CheckMemData(25, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 30, "1.1");
CheckMemData(30, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 30+25, "1.2");
ProcDone_V(2) := '1';
-- Unaligned end by timeout
WaitForCase(7, Clk);
CheckMemData(30, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 0, "1.0");
CheckMemData(29, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 30, "1.1");
CheckMemData(30, 0, Mem_DatData, Mem_DatVld, Mem_DatRdy, Clk, 30+29, "1.2");
ProcDone_V(2) := '1';
end procedure;
end;

View File

@@ -1,294 +0,0 @@
------------------------------------------------------------
-- Libraries
------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_common_logic_pkg.all;
use work.psi_common_array_pkg.all;
use work.psi_ms_daq_pkg.all;
library work;
use work.psi_tb_txt_util.all;
use work.psi_tb_compare_pkg.all;
use work.psi_tb_activity_pkg.all;
------------------------------------------------------------
-- Package Header
------------------------------------------------------------
package psi_ms_daq_daq_dma_tb_pkg is
-- *** Generics Record ***
type Generics_t is record
Dummy : boolean; -- required since empty records are not allowed
end record;
------------------------------------------------------------
-- Not exported Generics
------------------------------------------------------------
constant Streams_g : positive := 4;
------------------------------------------------------------
-- Procedures
------------------------------------------------------------
type EndType_s is (Trigger_s, Timeout_s, NoData_s, NoEnd_s);
procedure ApplyCmd( Stream : in integer;
Address : in integer;
MaxSize : in integer;
signal DaqSm_Cmd : out DaqSm2DaqDma_Cmd_t;
signal DaqSm_Cmd_Vld : out std_logic;
signal Clk : in std_logic);
procedure CheckResp( Stream : in integer;
Size : in integer;
EndType : in EndType_s;
signal DaqSm_Resp : in DaqDma2DaqSm_Resp_t;
signal DaqSm_Resp_Vld : in std_logic;
signal DaqSm_Resp_Rdy : out std_logic;
signal Clk : in std_logic);
procedure ApplyData( Stream : in integer;
Bytes : in integer;
EndType : in EndType_s;
signal Inp_Vld : out std_logic_vector;
signal Inp_Rdy : in std_logic_vector;
signal Inp_Data : out Input2Daq_Data_a;
signal Clk : in std_logic;
Offset : in integer := 0);
procedure CheckMemData( Bytes : in integer;
RdyDelay : in integer := 0;
signal Mem_DatData : in std_logic_vector;
signal Mem_DatVld : in std_logic;
signal Mem_DatRdy : out std_logic;
signal Clk : in std_logic;
Offset : in integer := 0;
Msg : in string := "");
procedure CheckMemCmd( Address : in integer;
Bytes : in integer;
RdyDelay : in integer := 0;
signal Mem_CmdAddr : in std_logic_vector;
signal Mem_CmdSize : in std_logic_vector;
signal Mem_CmdVld : in std_logic;
signal Mem_CmdRdy : out std_logic;
signal Clk : in std_logic;
Msg : in string := "");
shared variable TestCase_v : integer := -1;
shared variable ProcDone_V : std_logic_vector(0 to 2);
procedure InitCase( signal Clk : in std_logic;
signal Rst : out std_logic);
procedure InitSubCase(CaseNr : in integer);
procedure WaitForCase( CaseNr : in integer;
signal Clk : in std_logic);
procedure WaitAllProc( signal Clk : in std_logic);
end package;
------------------------------------------------------------
-- Package Body
------------------------------------------------------------
package body psi_ms_daq_daq_dma_tb_pkg is
procedure ApplyCmd( Stream : in integer;
Address : in integer;
MaxSize : in integer;
signal DaqSm_Cmd : out DaqSm2DaqDma_Cmd_t;
signal DaqSm_Cmd_Vld : out std_logic;
signal Clk : in std_logic) is
begin
wait until rising_edge(Clk);
DaqSm_Cmd_Vld <= '1';
DaqSm_Cmd.Address <= std_logic_vector(to_unsigned(Address, 32));
DaqSm_Cmd.MaxSize <= std_logic_vector(to_unsigned(MaxSize, 16));
DaqSm_Cmd.Stream <= Stream;
wait until rising_edge(Clk);
DaqSm_Cmd_Vld <= '0';
end procedure;
procedure CheckResp( Stream : in integer;
Size : in integer;
EndType : in EndType_s;
signal DaqSm_Resp : in DaqDma2DaqSm_Resp_t;
signal DaqSm_Resp_Vld : in std_logic;
signal DaqSm_Resp_Rdy : out std_logic;
signal Clk : in std_logic) is
begin
DaqSm_Resp_Rdy <= '1';
wait until rising_edge(Clk) and DaqSm_Resp_Vld = '1';
if Trigger_s = EndType then
StdlCompare(1, DaqSm_Resp.Trigger, "CHEK_RESP: Response has not set TRIGGER");
else
StdlCompare(0, DaqSm_Resp.Trigger, "CHEK_RESP: Response has not cleared TRIGGER");
end if;
StdlvCompareInt(Size, DaqSm_Resp.Size, "CHEK_RESP: Wrong size in response");
IntCompare(Stream, DaqSm_Resp.Stream, "CHEK_RESP: Wrong stream number in response");
wait until rising_edge(Clk);
StdlCompare(0, DaqSm_Resp_Vld, "CHEK_RESP: Response valid did not go low");
end procedure;
procedure ApplyData( Stream : in integer;
Bytes : in integer;
EndType : in EndType_s;
signal Inp_Vld : out std_logic_vector;
signal Inp_Rdy : in std_logic_vector;
signal Inp_Data : out Input2Daq_Data_a;
signal Clk : in std_logic;
Offset : in integer := 0) is
variable DataCnt_v : unsigned(7 downto 0) := to_unsigned(Offset, 8);
begin
assert EndType = NoEnd_s or EndType = Trigger_s or EndType = Timeout_s
report "###ERROR###: APPLY_DATA: EndType not yet implemented" severity error;
-- Empty frame handling
if Bytes = 0 then
Inp_Data(Stream).Data <= X"AAAA_BBBB_CCCC_DDDD";
Inp_Data(Stream).Bytes <= "0000";
if EndType = Timeout_s then
Inp_Data(Stream).Last <= '1';
Inp_Data(Stream).IsTo <= '1';
else
report "###ERROR###: APPLY_DATA: empty frames only supported for timeout" severity error;
end if;
wait until rising_edge(Clk) and Inp_Rdy(Stream) = '1';
Inp_Vld(Stream) <= '0';
-- Normal operation
else
Inp_Vld(Stream) <= '1';
for dw in 0 to (Bytes+7)/8-1 loop
for byte in 0 to 7 loop
if dw*8+byte >= Bytes then
Inp_Data(Stream).Data(8*(byte+1)-1 downto 8*byte) <= (others => '0');
else
Inp_Data(Stream).Data(8*(byte+1)-1 downto 8*byte) <= std_logic_vector(DataCnt_v);
DataCnt_v := DataCnt_v + 1;
end if;
end loop;
Inp_Data(Stream).Last <= '0';
Inp_Data(Stream).IsTo <= '0';
Inp_Data(Stream).IsTrig <= '0';
if dw = (Bytes+7)/8-1 then
if EndType = Trigger_s then
Inp_Data(Stream).Last <= '1';
Inp_Data(Stream).IsTrig <= '1';
elsif EndType = Timeout_s then
Inp_Data(Stream).Last <= '1';
Inp_Data(Stream).IsTo <= '1';
end if;
end if;
if Bytes-dw*8 > 8 then
Inp_Data(Stream).Bytes <= std_logic_vector(to_unsigned(8, 4));
else
Inp_Data(Stream).Bytes <= std_logic_vector(to_unsigned(Bytes-dw*8, 4));
end if;
wait until rising_edge(Clk) and Inp_Rdy(Stream) = '1';
end loop;
Inp_Vld(Stream) <= '0';
end if;
end procedure;
procedure CheckMemData( Bytes : in integer;
RdyDelay : in integer := 0;
signal Mem_DatData : in std_logic_vector;
signal Mem_DatVld : in std_logic;
signal Mem_DatRdy : out std_logic;
signal Clk : in std_logic;
Offset : in integer := 0;
Msg : in string := "") is
variable DataCnt_v : integer := Offset;
begin
for dw in 0 to (Bytes+7)/8-1 loop
if RdyDelay > 0 then
Mem_DatRdy <= '0';
for i in 0 to RdyDelay loop
wait until rising_edge(Clk);
end loop;
end if;
Mem_DatRdy <= '1';
wait until rising_edge(Clk) and Mem_DatVld = '1';
Mem_DatRdy <= '0';
for byte in 0 to 7 loop
if dw*8+byte >= Bytes then
-- nothing to compare
else
StdlvCompareInt (DataCnt_v, Mem_DatData(8*(byte+1)-1 downto 8*byte), "MEM_DATA: Wrong Data QW[" & to_string(dw) & "] Byte [" & to_string(byte) & "] - " & Msg, false);
DataCnt_v := (DataCnt_v + 1) mod 256;
end if;
end loop;
end loop;
end procedure;
procedure CheckMemCmd( Address : in integer;
Bytes : in integer;
RdyDelay : in integer := 0;
signal Mem_CmdAddr : in std_logic_vector;
signal Mem_CmdSize : in std_logic_vector;
signal Mem_CmdVld : in std_logic;
signal Mem_CmdRdy : out std_logic;
signal Clk : in std_logic;
Msg : in string := "") is
begin
if RdyDelay > 0 then
Mem_CmdRdy <= '0';
else
Mem_CmdRdy <= '1';
end if;
wait until rising_edge(Clk) and Mem_CmdVld = '1';
if RdyDelay > 0 then
for i in 0 to RdyDelay loop
wait until rising_edge(Clk);
end loop;
end if;
Mem_CmdRdy <= '1';
StdlCompare(1, Mem_CmdVld, "MEM CMD: Mem_CmdVld did not stay high - " & Msg);
StdlvCompareInt(Address, Mem_CmdAddr, "MEM_CMD: Wrong Address - " & Msg, false);
StdlvCompareInt(Bytes, Mem_CmdSize, "MEM_CMD: Wrong Size - " & Msg, false);
wait until rising_edge(Clk);
wait for 1 ns;
Mem_CmdRdy <= '0';
StdlCompare(0, Mem_CmdVld, "MEM_CMD: Mem_CmdVld did not go low - " & Msg);
end procedure;
procedure InitCase( signal Clk : in std_logic;
signal Rst : out std_logic) is
begin
ProcDone_V := (others => '0');
TestCase_v := -1;
wait until rising_edge(Clk);
Rst <= '1';
wait until rising_edge(Clk);
Rst <= '0';
wait until rising_edge(Clk);
end procedure;
procedure InitSubCase(CaseNr : in integer) is
begin
ProcDone_V := (others => '0');
TestCase_v := CaseNr;
end procedure;
procedure WaitForCase( CaseNr : in integer;
signal Clk : in std_logic) is
begin
while CaseNr /= TestCase_v loop
wait until rising_edge(Clk);
end loop;
end procedure;
procedure WaitAllProc( signal Clk : in std_logic) is
begin
while signed(ProcDone_V) /= -1 loop
wait until rising_edge(Clk);
end loop;
end procedure;
end;

View File

@@ -1,370 +0,0 @@
------------------------------------------------------------
-- Testbench generated by TbGen.py
------------------------------------------------------------
-- see Library/Python/TbGenerator
------------------------------------------------------------
-- Libraries
------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_common_array_pkg.all;
use work.psi_ms_daq_pkg.all;
library work;
use work.psi_tb_txt_util.all;
use work.psi_tb_compare_pkg.all;
library work;
use work.psi_ms_daq_daq_sm_tb_pkg.all;
library work;
use work.psi_ms_daq_daq_sm_tb_case_single_simple.all;
use work.psi_ms_daq_daq_sm_tb_case_priorities.all;
use work.psi_ms_daq_daq_sm_tb_case_single_window.all;
use work.psi_ms_daq_daq_sm_tb_case_multi_window.all;
use work.psi_ms_daq_daq_sm_tb_case_enable.all;
use work.psi_ms_daq_daq_sm_tb_case_irq.all;
use work.psi_ms_daq_daq_sm_tb_case_timestamp.all;
------------------------------------------------------------
-- Entity Declaration
------------------------------------------------------------
entity psi_ms_daq_daq_sm_tb is
end entity;
------------------------------------------------------------
-- Architecture
------------------------------------------------------------
architecture sim of psi_ms_daq_daq_sm_tb is
-- *** Fixed Generics ***
constant Streams_g : positive := 4;
constant StreamPrio_g : t_ainteger := (1, 2, 3, 1);
constant StreamWidth_g : t_ainteger := (8, 16, 32, 64);
constant Windows_g : positive := 8;
constant MinBurstSize_g : positive := 512;
constant MaxBurstSize_g : positive := 512;
-- *** Not Assigned Generics (default values) ***
-- *** Exported Generics ***
constant Generics_c : Generics_t := (
Dummy => true);
-- *** TB Control ***
signal TbRunning : boolean := True;
signal NextCase : integer := -1;
signal ProcessDone : std_logic_vector(0 to 3) := (others => '0');
constant AllProcessesDone_c : std_logic_vector(0 to 3) := (others => '1');
constant TbProcNr_control_c : integer := 0;
constant TbProcNr_dma_cmd_c : integer := 1;
constant TbProcNr_dma_resp_c : integer := 2;
constant TbProcNr_ctx_c : integer := 3;
-- *** DUT Signals ***
signal Clk : std_logic := '1';
signal Rst : std_logic := '0';
signal GlbEna : std_logic := '1';
signal StrEna : std_logic_vector(Streams_g-1 downto 0) := (others => '1');
signal StrIrq : std_logic_vector(Streams_g-1 downto 0) := (others => '0');
signal Inp_HasLast : std_logic_vector(Streams_g-1 downto 0) := (others => '0');
signal Inp_Level : t_aslv16(Streams_g-1 downto 0) := (others => (others => '0'));
signal Ts_Vld : std_logic_vector(Streams_g-1 downto 0) := (others => '0');
signal Ts_Rdy : std_logic_vector(Streams_g-1 downto 0) := (others => '0');
signal Ts_Data : t_aslv64(Streams_g-1 downto 0);
signal Dma_Cmd : DaqSm2DaqDma_Cmd_t;
signal Dma_Cmd_Vld : std_logic := '0';
signal Dma_Resp : DaqDma2DaqSm_Resp_t := ( Size => (others => '0'), Trigger => '0', Stream => 0);
signal Dma_Resp_Vld : std_logic := '0';
signal Dma_Resp_Rdy : std_logic := '0';
signal TfDone : std_logic := '0';
signal CtxStr_Cmd : ToCtxStr_t;
signal CtxStr_Resp : FromCtx_t := (others => (others => '0'));
signal CtxWin_Cmd : ToCtxWin_t;
signal CtxWin_Resp : FromCtx_t := (others => (others => '0'));
begin
------------------------------------------------------------
-- DUT Instantiation
------------------------------------------------------------
i_dut : entity work.psi_ms_daq_daq_sm
generic map (
Streams_g => Streams_g,
StreamPrio_g => StreamPrio_g,
StreamWidth_g => StreamWidth_g,
Windows_g => Windows_g,
MinBurstSize_g => MinBurstSize_g,
MaxBurstSize_g => MaxBurstSize_g
)
port map (
Clk => Clk,
Rst => Rst,
GlbEna => GlbEna,
StrEna => StrEna,
StrIrq => StrIrq,
Inp_HasLast => Inp_HasLast,
Inp_Level => Inp_Level,
Ts_Vld => Ts_Vld,
Ts_Rdy => Ts_Rdy,
Ts_Data => Ts_Data,
Dma_Cmd => Dma_Cmd,
Dma_Cmd_Vld => Dma_Cmd_Vld,
Dma_Resp => Dma_Resp,
Dma_Resp_Vld => Dma_Resp_Vld,
Dma_Resp_Rdy => Dma_Resp_Rdy,
TfDone => TfDone,
CtxStr_Cmd => CtxStr_Cmd,
CtxStr_Resp => CtxStr_Resp,
CtxWin_Cmd => CtxWin_Cmd,
CtxWin_Resp => CtxWin_Resp
);
------------------------------------------------------------
-- Testbench Control !DO NOT EDIT!
------------------------------------------------------------
p_tb_control : process
begin
-- single_simple
NextCase <= 0;
wait until ProcessDone = AllProcessesDone_c;
-- priorities
NextCase <= 1;
wait until ProcessDone = AllProcessesDone_c;
-- single_window
NextCase <= 2;
wait until ProcessDone = AllProcessesDone_c;
-- multi_window
NextCase <= 3;
wait until ProcessDone = AllProcessesDone_c;
-- enable
NextCase <= 4;
wait until ProcessDone = AllProcessesDone_c;
-- irq
NextCase <= 5;
wait until ProcessDone = AllProcessesDone_c;
-- timestamp
NextCase <= 6;
wait until ProcessDone = AllProcessesDone_c;
TbRunning <= false;
wait;
end process;
------------------------------------------------------------
-- Clocks !DO NOT EDIT!
------------------------------------------------------------
p_clock_Clk : process
constant Frequency_c : real := real(200e6);
begin
while TbRunning loop
wait for 0.5*(1 sec)/Frequency_c;
Clk <= not Clk;
end loop;
wait;
end process;
------------------------------------------------------------
-- Resets
------------------------------------------------------------
------------------------------------------------------------
-- Processes !DO NOT EDIT!
------------------------------------------------------------
-- *** control ***
p_control : process
begin
-- single_simple
wait until NextCase = 0;
ProcessDone(TbProcNr_control_c) <= '0';
work.psi_ms_daq_daq_sm_tb_case_single_simple.control(Clk, Rst, GlbEna, StrEna, StrIrq, Inp_HasLast, Inp_Level, Ts_Vld, Ts_Rdy, Ts_Data, Dma_Cmd, Dma_Cmd_Vld, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_control_c) <= '1';
-- priorities
wait until NextCase = 1;
ProcessDone(TbProcNr_control_c) <= '0';
work.psi_ms_daq_daq_sm_tb_case_priorities.control(Clk, Rst, GlbEna, StrEna, StrIrq, Inp_HasLast, Inp_Level, Ts_Vld, Ts_Rdy, Ts_Data, Dma_Cmd, Dma_Cmd_Vld, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_control_c) <= '1';
-- single_window
wait until NextCase = 2;
ProcessDone(TbProcNr_control_c) <= '0';
work.psi_ms_daq_daq_sm_tb_case_single_window.control(Clk, Rst, GlbEna, StrEna, StrIrq, Inp_HasLast, Inp_Level, Ts_Vld, Ts_Rdy, Ts_Data, Dma_Cmd, Dma_Cmd_Vld, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_control_c) <= '1';
-- multi_window
wait until NextCase = 3;
ProcessDone(TbProcNr_control_c) <= '0';
work.psi_ms_daq_daq_sm_tb_case_multi_window.control(Clk, Rst, GlbEna, StrEna, StrIrq, Inp_HasLast, Inp_Level, Ts_Vld, Ts_Rdy, Ts_Data, Dma_Cmd, Dma_Cmd_Vld, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_control_c) <= '1';
-- enable
wait until NextCase = 4;
ProcessDone(TbProcNr_control_c) <= '0';
work.psi_ms_daq_daq_sm_tb_case_enable.control(Clk, Rst, GlbEna, StrEna, StrIrq, Inp_HasLast, Inp_Level, Ts_Vld, Ts_Rdy, Ts_Data, Dma_Cmd, Dma_Cmd_Vld, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_control_c) <= '1';
-- irq
wait until NextCase = 5;
ProcessDone(TbProcNr_control_c) <= '0';
work.psi_ms_daq_daq_sm_tb_case_irq.control(Clk, Rst, GlbEna, StrEna, StrIrq, Inp_HasLast, Inp_Level, Ts_Vld, Ts_Rdy, Ts_Data, Dma_Cmd, Dma_Cmd_Vld, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_control_c) <= '1';
-- timestamp
wait until NextCase = 6;
ProcessDone(TbProcNr_control_c) <= '0';
work.psi_ms_daq_daq_sm_tb_case_timestamp.control(Clk, Rst, GlbEna, StrEna, StrIrq, Inp_HasLast, Inp_Level, Ts_Vld, Ts_Rdy, Ts_Data, Dma_Cmd, Dma_Cmd_Vld, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_control_c) <= '1';
wait;
end process;
-- *** dma_cmd ***
p_dma_cmd : process
begin
-- single_simple
wait until NextCase = 0;
ProcessDone(TbProcNr_dma_cmd_c) <= '0';
work.psi_ms_daq_daq_sm_tb_case_single_simple.dma_cmd(Clk, StrIrq, Dma_Cmd, Dma_Cmd_Vld, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_dma_cmd_c) <= '1';
-- priorities
wait until NextCase = 1;
ProcessDone(TbProcNr_dma_cmd_c) <= '0';
work.psi_ms_daq_daq_sm_tb_case_priorities.dma_cmd(Clk, StrIrq, Dma_Cmd, Dma_Cmd_Vld, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_dma_cmd_c) <= '1';
-- single_window
wait until NextCase = 2;
ProcessDone(TbProcNr_dma_cmd_c) <= '0';
work.psi_ms_daq_daq_sm_tb_case_single_window.dma_cmd(Clk, StrIrq, Dma_Cmd, Dma_Cmd_Vld, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_dma_cmd_c) <= '1';
-- multi_window
wait until NextCase = 3;
ProcessDone(TbProcNr_dma_cmd_c) <= '0';
work.psi_ms_daq_daq_sm_tb_case_multi_window.dma_cmd(Clk, StrIrq, Dma_Cmd, Dma_Cmd_Vld, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_dma_cmd_c) <= '1';
-- enable
wait until NextCase = 4;
ProcessDone(TbProcNr_dma_cmd_c) <= '0';
work.psi_ms_daq_daq_sm_tb_case_enable.dma_cmd(Clk, StrIrq, Dma_Cmd, Dma_Cmd_Vld, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_dma_cmd_c) <= '1';
-- irq
wait until NextCase = 5;
ProcessDone(TbProcNr_dma_cmd_c) <= '0';
work.psi_ms_daq_daq_sm_tb_case_irq.dma_cmd(Clk, StrIrq, Dma_Cmd, Dma_Cmd_Vld, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_dma_cmd_c) <= '1';
-- timestamp
wait until NextCase = 6;
ProcessDone(TbProcNr_dma_cmd_c) <= '0';
work.psi_ms_daq_daq_sm_tb_case_timestamp.dma_cmd(Clk, StrIrq, Dma_Cmd, Dma_Cmd_Vld, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_dma_cmd_c) <= '1';
wait;
end process;
-- *** dma_resp ***
p_dma_resp : process
begin
-- single_simple
wait until NextCase = 0;
ProcessDone(TbProcNr_dma_resp_c) <= '0';
work.psi_ms_daq_daq_sm_tb_case_single_simple.dma_resp(Clk, StrIrq, Dma_Resp, Dma_Resp_Vld, Dma_Resp_Rdy, TfDone, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_dma_resp_c) <= '1';
-- priorities
wait until NextCase = 1;
ProcessDone(TbProcNr_dma_resp_c) <= '0';
work.psi_ms_daq_daq_sm_tb_case_priorities.dma_resp(Clk, StrIrq, Dma_Resp, Dma_Resp_Vld, Dma_Resp_Rdy, TfDone, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_dma_resp_c) <= '1';
-- single_window
wait until NextCase = 2;
ProcessDone(TbProcNr_dma_resp_c) <= '0';
work.psi_ms_daq_daq_sm_tb_case_single_window.dma_resp(Clk, StrIrq, Dma_Resp, Dma_Resp_Vld, Dma_Resp_Rdy, TfDone, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_dma_resp_c) <= '1';
-- multi_window
wait until NextCase = 3;
ProcessDone(TbProcNr_dma_resp_c) <= '0';
work.psi_ms_daq_daq_sm_tb_case_multi_window.dma_resp(Clk, StrIrq, Dma_Resp, Dma_Resp_Vld, Dma_Resp_Rdy, TfDone, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_dma_resp_c) <= '1';
-- enable
wait until NextCase = 4;
ProcessDone(TbProcNr_dma_resp_c) <= '0';
work.psi_ms_daq_daq_sm_tb_case_enable.dma_resp(Clk, StrIrq, Dma_Resp, Dma_Resp_Vld, Dma_Resp_Rdy, TfDone, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_dma_resp_c) <= '1';
-- irq
wait until NextCase = 5;
ProcessDone(TbProcNr_dma_resp_c) <= '0';
work.psi_ms_daq_daq_sm_tb_case_irq.dma_resp(Clk, StrIrq, Dma_Resp, Dma_Resp_Vld, Dma_Resp_Rdy, TfDone, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_dma_resp_c) <= '1';
-- timestamp
wait until NextCase = 6;
ProcessDone(TbProcNr_dma_resp_c) <= '0';
work.psi_ms_daq_daq_sm_tb_case_timestamp.dma_resp(Clk, StrIrq, Dma_Resp, Dma_Resp_Vld, Dma_Resp_Rdy, TfDone, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_dma_resp_c) <= '1';
wait;
end process;
-- *** ctx ***
p_ctx : process
begin
-- single_simple
wait until NextCase = 0;
ProcessDone(TbProcNr_ctx_c) <= '0';
work.psi_ms_daq_daq_sm_tb_case_single_simple.ctx(Clk, CtxStr_Cmd, CtxStr_Resp, CtxWin_Cmd, CtxWin_Resp, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_ctx_c) <= '1';
-- priorities
wait until NextCase = 1;
ProcessDone(TbProcNr_ctx_c) <= '0';
work.psi_ms_daq_daq_sm_tb_case_priorities.ctx(Clk, CtxStr_Cmd, CtxStr_Resp, CtxWin_Cmd, CtxWin_Resp, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_ctx_c) <= '1';
-- single_window
wait until NextCase = 2;
ProcessDone(TbProcNr_ctx_c) <= '0';
work.psi_ms_daq_daq_sm_tb_case_single_window.ctx(Clk, CtxStr_Cmd, CtxStr_Resp, CtxWin_Cmd, CtxWin_Resp, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_ctx_c) <= '1';
-- multi_window
wait until NextCase = 3;
ProcessDone(TbProcNr_ctx_c) <= '0';
work.psi_ms_daq_daq_sm_tb_case_multi_window.ctx(Clk, CtxStr_Cmd, CtxStr_Resp, CtxWin_Cmd, CtxWin_Resp, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_ctx_c) <= '1';
-- enable
wait until NextCase = 4;
ProcessDone(TbProcNr_ctx_c) <= '0';
work.psi_ms_daq_daq_sm_tb_case_enable.ctx(Clk, CtxStr_Cmd, CtxStr_Resp, CtxWin_Cmd, CtxWin_Resp, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_ctx_c) <= '1';
-- irq
wait until NextCase = 5;
ProcessDone(TbProcNr_ctx_c) <= '0';
work.psi_ms_daq_daq_sm_tb_case_irq.ctx(Clk, CtxStr_Cmd, CtxStr_Resp, CtxWin_Cmd, CtxWin_Resp, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_ctx_c) <= '1';
-- timestamp
wait until NextCase = 6;
ProcessDone(TbProcNr_ctx_c) <= '0';
work.psi_ms_daq_daq_sm_tb_case_timestamp.ctx(Clk, CtxStr_Cmd, CtxStr_Resp, CtxWin_Cmd, CtxWin_Resp, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_ctx_c) <= '1';
wait;
end process;
end;

View File

@@ -1,577 +0,0 @@
------------------------------------------------------------
-- Libraries
------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_common_logic_pkg.all;
use work.psi_common_array_pkg.all;
use work.psi_ms_daq_pkg.all;
library work;
use work.psi_ms_daq_daq_sm_tb_pkg.all;
library work;
use work.psi_tb_txt_util.all;
use work.psi_tb_compare_pkg.all;
------------------------------------------------------------
-- Package Header
------------------------------------------------------------
package psi_ms_daq_daq_sm_tb_case_enable is
procedure control (
signal Clk : in std_logic;
signal Rst : inout std_logic;
signal GlbEna : inout std_logic;
signal StrEna : inout std_logic_vector;
signal StrIrq : in std_logic_vector;
signal Inp_HasLast : inout std_logic_vector;
signal Inp_Level : inout t_aslv16;
signal Ts_Vld : inout std_logic_vector;
signal Ts_Rdy : in std_logic_vector;
signal Ts_Data : inout t_aslv64;
signal Dma_Cmd : in DaqSm2DaqDma_Cmd_t;
signal Dma_Cmd_Vld : in std_logic;
constant Generics_c : Generics_t);
procedure dma_cmd (
signal Clk : in std_logic;
signal StrIrq : in std_logic_vector;
signal Dma_Cmd : in DaqSm2DaqDma_Cmd_t;
signal Dma_Cmd_Vld : in std_logic;
constant Generics_c : Generics_t);
procedure dma_resp (
signal Clk : in std_logic;
signal StrIrq : in std_logic_vector;
signal Dma_Resp : inout DaqDma2DaqSm_Resp_t;
signal Dma_Resp_Vld : inout std_logic;
signal Dma_Resp_Rdy : in std_logic;
signal TfDone : inout std_logic;
constant Generics_c : Generics_t);
procedure ctx (
signal Clk : in std_logic;
signal CtxStr_Cmd : in ToCtxStr_t;
signal CtxStr_Resp : inout FromCtx_t;
signal CtxWin_Cmd : in ToCtxWin_t;
signal CtxWin_Resp : inout FromCtx_t;
constant Generics_c : Generics_t);
end package;
------------------------------------------------------------
-- Package Body
------------------------------------------------------------
package body psi_ms_daq_daq_sm_tb_case_enable is
procedure control (
signal Clk : in std_logic;
signal Rst : inout std_logic;
signal GlbEna : inout std_logic;
signal StrEna : inout std_logic_vector;
signal StrIrq : in std_logic_vector;
signal Inp_HasLast : inout std_logic_vector;
signal Inp_Level : inout t_aslv16;
signal Ts_Vld : inout std_logic_vector;
signal Ts_Rdy : in std_logic_vector;
signal Ts_Data : inout t_aslv64;
signal Dma_Cmd : in DaqSm2DaqDma_Cmd_t;
signal Dma_Cmd_Vld : in std_logic;
constant Generics_c : Generics_t) is
begin
print(">> -- enable --");
-- Disabled stream does not react (global)
print(">> Disabled stream does not react (global)");
InitTestCase(Clk, Rst);
GlbEna <= '0';
wait for 100 ns;
TestCase := 0;
ConfigureAuto( WinSize => 4096*2, Ringbuf => '0', Overwrite => '1', Wincnt => 2, Wincur => 0);
for i in 0 to 3 loop
Inp_Level(i) <= LvlThreshold_c;
end loop;
wait for 1 us;
for i in 0 to 3 loop
Inp_Level(i) <= (others => '0');
end loop;
GlbEna <= '1';
ControlWaitCompl(Clk);
-- Disabled stream does not react (per stream)
print(">> Disabled stream does not react (per stream)");
InitTestCase(Clk, Rst);
TestCase := 1;
ConfigureAuto( WinSize => 4096*2, Ringbuf => '0', Overwrite => '1', Wincnt => 2, Wincur => 0);
for i in 0 to 3 loop
StrEna(i) <= '0';
wait for 20 ns;
Inp_Level(i) <= LvlThreshold_c;
wait for 1 us;
Inp_Level(i) <= (others => '0');
StrEna(i) <= '1';
end loop;
ControlWaitCompl(Clk);
-- Disabled stream does not influence arbitration
print(">> Disabled stream does not react (per stream)");
InitTestCase(Clk, Rst);
TestCase := 2;
ConfigureAuto( WinSize => 4096*2, Ringbuf => '0', Overwrite => '1', Wincnt => 2, Wincur => 0);
StrEna(0) <= '0';
wait for 20 ns;
Inp_Level(0) <= LvlThreshold_c;
wait for 200 ns;
Inp_Level(1) <= LvlThreshold_c;
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
Inp_Level(0) <= (others => '0');
Inp_Level(1) <= (others => '0');
StrEna(0) <= '1';
ControlWaitCompl(Clk);
-- Start with Sample 0, Window 0 after enable (global)
print(">> Start with Sample 0, Window 0 after enable (global)");
InitTestCase(Clk, Rst);
TestCase := 3;
for i in 0 to 2 loop
Inp_Level(0) <= LvlThreshold_c;
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
Inp_Level(0) <= (others => '0');
wait for 500 ns;
Inp_Level(1) <= LvlThreshold_c;
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
Inp_Level(1) <= (others => '0');
wait for 500 ns;
-- Shortly disable al lstreams after first access
if i = 1 then
GlbEna <= '0';
wait for 20 ns;
GlbEna <= '1';
wait for 20 ns;
end if;
end loop;
ControlWaitCompl(Clk);
-- Start with Sample 0, Window 0 after enable (per stream)
-- only reset stream 0
print(">> Start with Sample 0, Window 0 after enable (per stream)");
InitTestCase(Clk, Rst);
TestCase := 4;
for i in 0 to 2 loop
Inp_Level(0) <= LvlThreshold_c;
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
Inp_Level(0) <= (others => '0');
wait for 500 ns;
Inp_Level(1) <= LvlThreshold_c;
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
Inp_Level(1) <= (others => '0');
wait for 500 ns;
-- Shortly disable al lstreams after first access
if i = 1 then
StrEna(0) <= '0';
wait for 20 ns;
StrEna(0) <= '1';
wait for 20 ns;
end if;
end loop;
ControlWaitCompl(Clk);
-- 4k Boundary (is 4k boundary reset correctly for the first sample)
print(">> 4k Boundary");
InitTestCase(Clk, Rst);
TestCase := 5;
Inp_Level(0) <= LvlThreshold_c;
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
Inp_Level(0) <= (others => '0');
StrEna(0) <= '0';
wait for 20 ns;
StrEna(0) <= '1';
wait for 20 ns;
Inp_Level(0) <= LvlThreshold_c;
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
Inp_Level(0) <= (others => '0');
ControlWaitCompl(Clk);
end procedure;
procedure dma_cmd (
signal Clk : in std_logic;
signal StrIrq : in std_logic_vector;
signal Dma_Cmd : in DaqSm2DaqDma_Cmd_t;
signal Dma_Cmd_Vld : in std_logic;
constant Generics_c : Generics_t) is
variable StartTime_v : time;
begin
-- Disabled stream does not react (global)
WaitForCase(0, Clk);
StartTime_v := now;
while now < StartTime_v + 1 us loop
StdlCompare(0, Dma_Cmd_Vld, "Unexpected DMA command");
wait until rising_edge(Clk);
end loop;
ProcDone(2) := '1';
-- Disabled stream does not react (per stream)
WaitForCase(1, Clk);
for str in 0 to 3 loop
StartTime_v := now;
while now < StartTime_v + 1 us loop
StdlCompare(0, Dma_Cmd_Vld, "Unexpected DMA command");
wait until rising_edge(Clk);
end loop;
end loop;
ProcDone(2) := '1';
-- Disabled stream does not influence arbitration
WaitForCase(2, Clk);
-- Win0
ExpectDmaCmdAuto( Stream => 1, MaxSize => 4096, Msg => "Wr0.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ProcDone(2) := '1';
-- Start with Sampe 0, Window 0 after enable (global)
WaitForCase(3, Clk);
-- First after reset
ExpectDmaCmd( Stream => 0, Address => 16#01200000#, MaxSize => 4096, Msg=>"0.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmd( Stream => 1, Address => 16#01210000#, MaxSize => 4096, Msg=>"0.1",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
-- Normal
ExpectDmaCmd( Stream => 0, Address => 16#01208000#, MaxSize => 4096, Msg=>"1.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmd( Stream => 1, Address => 16#01218000#, MaxSize => 4096, Msg=>"1.1",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
-- First after disable
ExpectDmaCmd( Stream => 0, Address => 16#01200000#, MaxSize => 4096, Msg=>"2.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmd( Stream => 1, Address => 16#01210000#, MaxSize => 4096, Msg=>"2.1",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ProcDone(2) := '1';
-- Start with Sampe 0, Window 0 after enable (per stream)
WaitForCase(4, Clk);
-- First after reset
ExpectDmaCmd( Stream => 0, Address => 16#01200000#, MaxSize => 4096, Msg=>"0.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmd( Stream => 1, Address => 16#01210000#, MaxSize => 4096, Msg=>"0.1",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
-- Normal
ExpectDmaCmd( Stream => 0, Address => 16#01208000#, MaxSize => 4096, Msg=>"1.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmd( Stream => 1, Address => 16#01218000#, MaxSize => 4096, Msg=>"1.1",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
-- First after disable for stream 0
ExpectDmaCmd( Stream => 0, Address => 16#01200000#, MaxSize => 4096, Msg=>"2.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
-- Stream 1 continues normally
ExpectDmaCmd( Stream => 1, Address => 16#01218000#, MaxSize => 4096, Msg=>"2.1",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ProcDone(2) := '1';
-- 4k Boundary
WaitForCase(5, Clk);
-- First after reset
ExpectDmaCmd( Stream => 0, Address => 16#01200800#, MaxSize => 2048, Msg=>"0.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
-- Normal
ExpectDmaCmd( Stream => 0, Address => 16#01208000#, MaxSize => 4096, Msg=>"0.1",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
-- First after disable for stream 0
ExpectDmaCmd( Stream => 0, Address => 16#01200800#, MaxSize => 2048, Msg=>"1.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
-- Normal
ExpectDmaCmd( Stream => 0, Address => 16#01208000#, MaxSize => 4096, Msg=>"1.1",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ProcDone(2) := '1';
end procedure;
procedure dma_resp (
signal Clk : in std_logic;
signal StrIrq : in std_logic_vector;
signal Dma_Resp : inout DaqDma2DaqSm_Resp_t;
signal Dma_Resp_Vld : inout std_logic;
signal Dma_Resp_Rdy : in std_logic;
signal TfDone : inout std_logic;
constant Generics_c : Generics_t) is
begin
-- Disabled stream does not react (global)
WaitForCase(0, Clk);
ProcDone(1) := '1';
-- Disabled stream does not react (per stream)
WaitForCase(1, Clk);
ProcDone(1) := '1';
-- Disabled stream does not influence arbitration
WaitForCase(2, Clk);
ApplyDmaRespAuto( Stream => 1, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ProcDone(1) := '1';
-- Start with Sampe 0, Window 0 after enable (global)
WaitForCase(3, Clk);
for i in 0 to 2 loop
ApplyDmaResp( Stream => 0, Size => 4096, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaResp( Stream => 1, Size => 4096, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
end loop;
ProcDone(1) := '1';
-- Start with Sampe 0, Window 0 after enable (per stream)
WaitForCase(4, Clk);
for i in 0 to 2 loop
ApplyDmaResp( Stream => 0, Size => 4096, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaResp( Stream => 1, Size => 4096, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
end loop;
ProcDone(1) := '1';
-- 4k Boundary
WaitForCase(5, Clk);
for i in 0 to 1 loop
for k in 0 to 1 loop
ApplyDmaResp( Stream => 0, Size => 2048+k*2048, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
end loop;
end loop;
ProcDone(1) := '1';
end procedure;
procedure ctx (
signal Clk : in std_logic;
signal CtxStr_Cmd : in ToCtxStr_t;
signal CtxStr_Resp : inout FromCtx_t;
signal CtxWin_Cmd : in ToCtxWin_t;
signal CtxWin_Resp : inout FromCtx_t;
constant Generics_c : Generics_t) is
variable StartTime_v : time;
variable CurPtr_v : integer;
variable BufStart_v : integer;
variable NextPtr_v : integer;
variable WinNext_v : integer;
variable SplWinBefore_v : integer;
variable SplWinAfter_v : integer;
variable TfSize_v : integer;
begin
-- Disabled stream does not react (global)
WaitForCase(0, Clk);
StartTime_v := now;
while now < StartTime_v + 1 us loop
StdlCompare(0, CtxStr_Cmd.WenLo, "CtxStr_Cmd.WenLo high unexpectedly");
StdlCompare(0, CtxStr_Cmd.WenHi, "CtxStr_Cmd.WenHi high unexpectedly");
StdlCompare(0, CtxWin_Cmd.WenLo, "CtxWin_Cmd.WenLo high unexpectedly");
StdlCompare(0, CtxWin_Cmd.WenHi, "CtxWin_Cmd.WenHi high unexpectedly");
StdlCompare(0, CtxWin_Cmd.Rd, "CtxWin_Cmd.Rd high unexpectedly");
wait until rising_edge(Clk);
end loop;
ProcDone(0) := '1';
-- Disabled stream does not react (per stream)
WaitForCase(1, Clk);
for str in 0 to 3 loop
StartTime_v := now;
while now < StartTime_v + 1 us loop
StdlCompare(0, CtxStr_Cmd.WenLo, "CtxStr_Cmd.WenLo high unexpectedly");
StdlCompare(0, CtxStr_Cmd.WenHi, "CtxStr_Cmd.WenHi high unexpectedly");
StdlCompare(0, CtxWin_Cmd.WenLo, "CtxWin_Cmd.WenLo high unexpectedly");
StdlCompare(0, CtxWin_Cmd.WenHi, "CtxWin_Cmd.WenHi high unexpectedly");
StdlCompare(0, CtxWin_Cmd.Rd, "CtxWin_Cmd.Rd high unexpectedly");
wait until rising_edge(Clk);
end loop;
end loop;
ProcDone(0) := '1';
-- Disabled stream does not influence arbitration
WaitForCase(2, Clk);
ExpCtxFullBurstAuto( Stream => 1, Msg => "Wr0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ProcDone(0) := '1';
-- Start with Sampe 0, Window 0 after enable (global)
WaitForCase(3, Clk);
for i in 0 to 2 loop
for str in 0 to 1 loop
-- Read for calculation of access
BufStart_v := 16#01200000# + 16#00010000#*str;
CurPtr_v := BufStart_v + 16#8000#;
if i = 1 then
NextPtr_v := CurPtr_v + 4096;
WinNext_v := 2;
SplWinBefore_v := 4096/(StreamWidth_g(str)/8);
else
NextPtr_v := BufStart_v + 4096;
WinNext_v := 0;
SplWinBefore_v := 0;
end if;
SplWinAfter_v := SplWinBefore_v + 4096/(StreamWidth_g(str)/8);
ExpCtxRead( Stream => Str,
BufStart => BufStart_v,
WinSize => 16#00004000#,
Overwrite => '1',
Ptr => CurPtr_v,
Wincnt => 4,
Wincur => 2,
WinSel => WinNext_v,
SamplesWin => SplWinBefore_v,
Msg => "a" & to_string(i) & "." & to_string(str),
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
-- Read for update
ExpCtxRead( Stream => Str,
BufStart => BufStart_v,
WinSize => 16#00004000#,
Overwrite => '1',
Ptr => CurPtr_v,
Wincnt => 4,
Wincur => WinNext_v,
WinSel => WinNext_v,
SamplesWin => SplWinBefore_v,
Msg => "b" & to_string(i) & "." & to_string(str),
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
-- Write of update
ExpCtxWrite( Stream => Str,
BufStart => BufStart_v,
WinSize => 16#00004000#,
Overwrite => '1',
Ptr => NextPtr_v,
Wincnt => 4,
Wincur => WinNext_v,
WinNext => WinNext_v,
SamplesWin => SplWinAfter_v,
WinLast => NextPtr_v-StreamWidth_g(str)/8,
Msg => "" & to_string(i) & "." & to_string(str),
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxWin_Cmd => CtxWin_Cmd);
end loop;
end loop;
ProcDone(0) := '1';
-- Start with Sampe 0, Window 0 after enable (per stream)
WaitForCase(4, Clk);
for i in 0 to 2 loop
for str in 0 to 1 loop
-- Read for calculation of access
BufStart_v := 16#01200000# + 16#00010000#*str;
CurPtr_v := BufStart_v + 16#8000#;
if (i = 0) or (i = 2 and str = 0) then
NextPtr_v := BufStart_v + 4096;
WinNext_v := 0;
SplWinBefore_v := 0;
else
NextPtr_v := CurPtr_v + 4096;
WinNext_v := 2;
SplWinBefore_v := 4096/(StreamWidth_g(str)/8);
end if;
SplWinAfter_v := SplWinBefore_v + 4096/(StreamWidth_g(str)/8);
ExpCtxRead( Stream => Str,
BufStart => BufStart_v,
WinSize => 16#00004000#,
Overwrite => '1',
Ptr => CurPtr_v,
Wincnt => 4,
Wincur => 2,
WinSel => WinNext_v,
SamplesWin => SplWinBefore_v,
Msg => "a" & to_string(i) & "." & to_string(str),
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
-- Read for update
ExpCtxRead( Stream => Str,
BufStart => BufStart_v,
WinSize => 16#00004000#,
Overwrite => '1',
Ptr => CurPtr_v,
Wincnt => 4,
Wincur => WinNext_v,
WinSel => WinNext_v,
SamplesWin => SplWinBefore_v,
Msg => "b" & to_string(i) & "." & to_string(str),
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
-- Write of update
ExpCtxWrite( Stream => Str,
BufStart => BufStart_v,
WinSize => 16#00004000#,
Overwrite => '1',
Ptr => NextPtr_v,
Wincnt => 4,
Wincur => WinNext_v,
WinNext => WinNext_v,
SamplesWin => SplWinAfter_v,
WinLast => NextPtr_v-StreamWidth_g(str)/8,
Msg => "" & to_string(i) & "." & to_string(str),
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxWin_Cmd => CtxWin_Cmd);
end loop;
end loop;
ProcDone(0) := '1';
-- 4k Boundary
WaitForCase(5, Clk);
for i in 0 to 3 loop
-- Read for calculation of access
BufStart_v := 16#01200800#;
CurPtr_v := 16#01208000#;
-- If first after reset/enable
if (i = 0) or (i = 2) then
TfSize_v := 2048;
NextPtr_v := BufStart_v + TfSize_v;
WinNext_v := 0;
SplWinBefore_v := 0;
else
TfSize_v := 4096;
NextPtr_v := CurPtr_v + TfSize_v;
WinNext_v := 2;
SplWinBefore_v := 4096/(StreamWidth_g(0)/8);
end if;
SplWinAfter_v := SplWinBefore_v + TfSize_v/(StreamWidth_g(0)/8);
ExpCtxRead( Stream => 0,
BufStart => BufStart_v,
WinSize => 16#00004000#,
Overwrite => '1',
Ptr => CurPtr_v,
Wincnt => 4,
Wincur => 2,
WinSel => WinNext_v,
SamplesWin => SplWinBefore_v,
Msg => "a" & to_string(i),
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
-- Read for update
ExpCtxRead( Stream => 0,
BufStart => BufStart_v,
WinSize => 16#00004000#,
Overwrite => '1',
Ptr => CurPtr_v,
Wincnt => 4,
Wincur => WinNext_v,
WinSel => WinNext_v,
SamplesWin => SplWinBefore_v,
Msg => "b" & to_string(i),
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
-- Write of update
ExpCtxWrite( Stream => 0,
BufStart => BufStart_v,
WinSize => 16#00004000#,
Overwrite => '1',
Ptr => NextPtr_v,
Wincnt => 4,
Wincur => WinNext_v,
WinNext => WinNext_v,
SamplesWin => SplWinAfter_v,
WinLast => NextPtr_v-StreamWidth_g(0)/8,
Msg => "c" & to_string(i),
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxWin_Cmd => CtxWin_Cmd);
end loop;
ProcDone(0) := '1';
end procedure;
end;

View File

@@ -1,392 +0,0 @@
------------------------------------------------------------
-- Libraries
------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_common_logic_pkg.all;
use work.psi_common_array_pkg.all;
use work.psi_ms_daq_pkg.all;
library work;
use work.psi_ms_daq_daq_sm_tb_pkg.all;
library work;
use work.psi_tb_txt_util.all;
use work.psi_tb_compare_pkg.all;
use work.psi_tb_activity_pkg.all;
------------------------------------------------------------
-- Package Header
------------------------------------------------------------
package psi_ms_daq_daq_sm_tb_case_irq is
procedure control (
signal Clk : in std_logic;
signal Rst : inout std_logic;
signal GlbEna : inout std_logic;
signal StrEna : inout std_logic_vector;
signal StrIrq : in std_logic_vector;
signal Inp_HasLast : inout std_logic_vector;
signal Inp_Level : inout t_aslv16;
signal Ts_Vld : inout std_logic_vector;
signal Ts_Rdy : in std_logic_vector;
signal Ts_Data : inout t_aslv64;
signal Dma_Cmd : in DaqSm2DaqDma_Cmd_t;
signal Dma_Cmd_Vld : in std_logic;
constant Generics_c : Generics_t);
procedure dma_cmd (
signal Clk : in std_logic;
signal StrIrq : in std_logic_vector;
signal Dma_Cmd : in DaqSm2DaqDma_Cmd_t;
signal Dma_Cmd_Vld : in std_logic;
constant Generics_c : Generics_t);
procedure dma_resp (
signal Clk : in std_logic;
signal StrIrq : in std_logic_vector;
signal Dma_Resp : inout DaqDma2DaqSm_Resp_t;
signal Dma_Resp_Vld : inout std_logic;
signal Dma_Resp_Rdy : in std_logic;
signal TfDone : inout std_logic;
constant Generics_c : Generics_t);
procedure ctx (
signal Clk : in std_logic;
signal CtxStr_Cmd : in ToCtxStr_t;
signal CtxStr_Resp : inout FromCtx_t;
signal CtxWin_Cmd : in ToCtxWin_t;
signal CtxWin_Resp : inout FromCtx_t;
constant Generics_c : Generics_t);
end package;
------------------------------------------------------------
-- Package Body
------------------------------------------------------------
package body psi_ms_daq_daq_sm_tb_case_irq is
procedure control (
signal Clk : in std_logic;
signal Rst : inout std_logic;
signal GlbEna : inout std_logic;
signal StrEna : inout std_logic_vector;
signal StrIrq : in std_logic_vector;
signal Inp_HasLast : inout std_logic_vector;
signal Inp_Level : inout t_aslv16;
signal Ts_Vld : inout std_logic_vector;
signal Ts_Rdy : in std_logic_vector;
signal Ts_Data : inout t_aslv64;
signal Dma_Cmd : in DaqSm2DaqDma_Cmd_t;
signal Dma_Cmd_Vld : in std_logic;
constant Generics_c : Generics_t) is
begin
print(">> -- irq --");
-- Normal Order
print(">> Normal Order");
InitTestCase(Clk, Rst);
TestCase := 0;
ConfigureAuto( WinSize => 4096, Ringbuf => '0', Overwrite => '1', Wincnt => 2, Wincur => 0);
Inp_Level(0) <= LvlThreshold_c;
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
Inp_Level(0) <= (others => '0');
ControlWaitCompl(Clk);
-- Flipped Order
print(">> Flipped Order");
InitTestCase(Clk, Rst);
TestCase := 1;
ConfigureAuto( WinSize => 4096, Ringbuf => '0', Overwrite => '1', Wincnt => 2, Wincur => 0);
Inp_Level(0) <= LvlThreshold_c;
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
Inp_Level(0) <= (others => '0');
ControlWaitCompl(Clk);
-- IRQ FIFO full
-- ... FIFO is full after Streams (4) x 3 = 12 open transfers
print(">> IRQ FIFO full");
InitTestCase(Clk, Rst);
TestCase := 2;
ConfigureAuto( WinSize => 4096, Ringbuf => '0', Overwrite => '1', Wincnt => 2, Wincur => 0);
Inp_Level(0) <= LvlThreshold_c;
-- Fill FIFO
for i in 0 to 11 loop
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
end loop;
-- Checked transfer
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
Inp_Level(0) <= (others => '0');
ControlWaitCompl(Clk);
-- Multi-Stream
wait for 1 us;
print(">> Multi-Stream");
InitTestCase(Clk, Rst);
TestCase := 3;
ConfigureAuto( WinSize => 4096, Ringbuf => '0', Overwrite => '1', Wincnt => 2, Wincur => 0);
for i in 3 downto 0 loop
Inp_Level(i) <= LvlThreshold_c;
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
Inp_Level(i) <= (others => '0');
wait for 200 ns;
end loop;
ControlWaitCompl(Clk);
-- Win-Change without trigger
wait for 1 us;
print(">> Win-Change without trigger");
InitTestCase(Clk, Rst);
TestCase := 4;
ConfigureAuto( WinSize => 4096*2, Ringbuf => '0', Overwrite => '1', Wincnt => 2, Wincur => 0);
Inp_Level(0) <= LvlThreshold_c;
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
Inp_Level(0) <= (others => '0');
ControlWaitCompl(Clk);
-- No IRQ on Ringbuf Wrap
print(">> No IRQ on Ringbuf Wrap");
InitTestCase(Clk, Rst);
TestCase := 5;
ConfigureAuto( WinSize => 4096*2, Ringbuf => '1', Overwrite => '1', Wincnt => 2, Wincur => 0);
Inp_Level(0) <= LvlThreshold_c;
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
Inp_Level(0) <= (others => '0');
ControlWaitCompl(Clk);
end procedure;
procedure dma_cmd (
signal Clk : in std_logic;
signal StrIrq : in std_logic_vector;
signal Dma_Cmd : in DaqSm2DaqDma_Cmd_t;
signal Dma_Cmd_Vld : in std_logic;
constant Generics_c : Generics_t) is
begin
-- Normal Order
WaitForCase(0, Clk);
ExpectDmaCmdAuto( Stream => 0, MaxSize => 4096, ExeSize=> 512, Msg => "Wr0.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ProcDone(2) := '1';
-- Flipped Order
WaitForCase(1, Clk);
ExpectDmaCmdAuto( Stream => 0, MaxSize => 4096, ExeSize=> 512, Msg => "Wr0.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ProcDone(2) := '1';
-- IRQ FIFO full
WaitForCase(2, Clk);
-- Fill FIFO
for i in 0 to 11 loop
ExpectDmaCmdAuto( Stream => 0, MaxSize => 4096, ExeSize=> 512, Msg => "Wr" & to_string(i), NextWin => true,
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
end loop;
-- Checked transfer
CheckNoActivity(Dma_Cmd_Vld, 1 us, 0, "Full");
ExpectDmaCmdAuto( Stream => 0, MaxSize => 4096, ExeSize=> 512, Msg => "Wr12", NextWin => true,
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ProcDone(2) := '1';
-- Multi-Stream
WaitForCase(3, Clk);
for i in 3 downto 0 loop
ExpectDmaCmdAuto( Stream => i, MaxSize => 4096, ExeSize=> 512*(i+1), Msg => "Wr" & to_string(i), NextWin => true,
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
end loop;
ProcDone(2) := '1';
-- Win-Change without trigger
WaitForCase(4, Clk);
ExpectDmaCmdAuto( Stream => 0, MaxSize => 4096, Msg => "Wr0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 0, MaxSize => 4096, Msg => "Wr0", NextWin => true,
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 0, MaxSize => 4096, Msg => "Wr0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ProcDone(2) := '1';
-- No IRQ on Ringbuf Wrap
WaitForCase(5, Clk);
ExpectDmaCmdAuto( Stream => 0, MaxSize => 4096, Msg => "Wr0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 0, MaxSize => 4096, Msg => "Wr0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 0, MaxSize => 4096, Msg => "Wr0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ProcDone(2) := '1';
end procedure;
procedure dma_resp (
signal Clk : in std_logic;
signal StrIrq : in std_logic_vector;
signal Dma_Resp : inout DaqDma2DaqSm_Resp_t;
signal Dma_Resp_Vld : inout std_logic;
signal Dma_Resp_Rdy : in std_logic;
signal TfDone : inout std_logic;
constant Generics_c : Generics_t) is
begin
-- Normal Order
WaitForCase(0, Clk);
ApplyDmaRespAuto( Stream => 0, Trigger => '1',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
wait for 200 ns;
StdlvCompareStdlv ("0000", StrIrq, "IRQs asserted unexpectedly");
assert StrIrq'last_event > 200 ns report "###ERROR###: IRQs not idle" severity error;
AssertTfDone(Clk, TfDone);
CheckIrq(MaxWait => (1 us), Stream => 0, Clk => Clk, StrIrq => StrIrq);
ProcDone(1) := '1';
-- Flipped Order
WaitForCase(1, Clk);
AssertTfDone(Clk, TfDone);
wait for 200 ns;
StdlvCompareStdlv ("0000", StrIrq, "IRQs asserted unexpectedly");
assert StrIrq'last_event > 200 ns report "###ERROR###: IRQs not idle" severity error;
ApplyDmaRespAuto( Stream => 0, Trigger => '1',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
CheckIrq(MaxWait => (1 us), Stream => 0, Clk => Clk, StrIrq => StrIrq);
ProcDone(1) := '1';
-- IRQ FIFO full
WaitForCase(2, Clk);
-- Fill FIFO
for i in 0 to 11 loop
ApplyDmaRespAuto( Stream => 0, Trigger => '1',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
end loop;
-- Wait
wait for 1.1 us;
-- Send IRQs
for i in 0 to 11 loop
AssertTfDone(Clk, TfDone);
CheckIrq(MaxWait => (1 us), Stream => 0, Clk => Clk, StrIrq => StrIrq);
end loop;
-- Last transfer
ApplyDmaRespAuto( Stream => 0, Trigger => '1',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
AssertTfDone(Clk, TfDone);
CheckIrq(MaxWait => (1 us), Stream => 0, Clk => Clk, StrIrq => StrIrq);
ProcDone(1) := '1';
-- Multi-Stream
WaitForCase(3, Clk);
for i in 3 downto 0 loop
ApplyDmaRespAuto( Stream => i, Trigger => '1',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
end loop;
for i in 3 downto 0 loop
AssertTfDone(Clk, TfDone);
CheckIrq(MaxWait => (1 us), Stream => i, Clk => Clk, StrIrq => StrIrq);
end loop;
ProcDone(1) := '1';
-- Win-Change without trigger
WaitForCase(4, Clk);
wait for 100 ns;
ApplyDmaRespAuto( Stream => 0, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
AssertTfDone(Clk, TfDone);
CheckNoActivityStlv(StrIrq, 100 ns, 0, "Before Window Change");
wait for 100 ns;
ApplyDmaRespAuto( Stream => 0, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
AssertTfDone(Clk, TfDone);
CheckIrq(MaxWait => (1 us), Stream => 0, Clk => Clk, StrIrq => StrIrq);
wait for 100 ns;
ApplyDmaRespAuto( Stream => 0, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
AssertTfDone(Clk, TfDone);
CheckNoActivityStlv(StrIrq, 100 ns, 0, "After Window Change");
ProcDone(1) := '1';
-- No IRQ on Ringbuf Wrap
WaitForCase(5, Clk);
wait for 100 ns;
ApplyDmaRespAuto( Stream => 0, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
AssertTfDone(Clk, TfDone);
CheckNoActivityStlv(StrIrq, 100 ns, 0, "Before Wrap");
wait for 100 ns;
ApplyDmaRespAuto( Stream => 0, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
AssertTfDone(Clk, TfDone);
CheckNoActivityStlv(StrIrq, 100 ns, 0, "Wrap");
wait for 100 ns;
ApplyDmaRespAuto( Stream => 0, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
AssertTfDone(Clk, TfDone);
CheckNoActivityStlv(StrIrq, 100 ns, 0, "After Wrap");
ProcDone(1) := '1';
end procedure;
procedure ctx (
signal Clk : in std_logic;
signal CtxStr_Cmd : in ToCtxStr_t;
signal CtxStr_Resp : inout FromCtx_t;
signal CtxWin_Cmd : in ToCtxWin_t;
signal CtxWin_Resp : inout FromCtx_t;
constant Generics_c : Generics_t) is
begin
-- Normal Order
WaitForCase(0, Clk);
ExpCtxFullBurstAuto( Stream => 0, Msg => "Wr0.0", NextWin => true, IsTrig => true,
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ProcDone(0) := '1';
-- Flipped Order
WaitForCase(1, Clk);
ExpCtxFullBurstAuto( Stream => 0, Msg => "Wr0.0", NextWin => true, IsTrig => true,
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ProcDone(0) := '1';
-- IRQ FIFO full
WaitForCase(2, Clk);
for i in 0 to 11 loop
ExpCtxFullBurstAuto( Stream => 0, NextWin => true, IsTrig => true,
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
end loop;
ExpCtxFullBurstAuto( Stream => 0, NextWin => true, IsTrig => true,
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ProcDone(0) := '1';
-- Multi-Stream
WaitForCase(3, Clk);
for i in 3 downto 0 loop
ExpCtxFullBurstAuto( Stream => i, NextWin => true, IsTrig => true,
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
end loop;
ProcDone(0) := '1';
-- Win-Change without trigger
WaitForCase(4, Clk);
ExpCtxFullBurstAuto( Stream => 0, Msg => "Wr0.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 0, Msg => "Wr0.1", NextWin => true,
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 0, Msg => "Wr1.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ProcDone(0) := '1';
-- No IRQ on Ringbuf Wrap
WaitForCase(5, Clk);
ExpCtxFullBurstAuto( Stream => 0, Msg => "Wr0.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 0, Msg => "Wr0.1",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 0, Msg => "Wr0.2",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ProcDone(0) := '1';
end procedure;
end;

View File

@@ -1,483 +0,0 @@
------------------------------------------------------------
-- Libraries
------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_common_array_pkg.all;
use work.psi_ms_daq_pkg.all;
library work;
use work.psi_ms_daq_daq_sm_tb_pkg.all;
library work;
use work.psi_tb_txt_util.all;
use work.psi_tb_compare_pkg.all;
------------------------------------------------------------
-- Package Header
------------------------------------------------------------
package psi_ms_daq_daq_sm_tb_case_multi_window is
procedure control (
signal Clk : in std_logic;
signal Rst : inout std_logic;
signal GlbEna : inout std_logic;
signal StrEna : inout std_logic_vector;
signal StrIrq : in std_logic_vector;
signal Inp_HasLast : inout std_logic_vector;
signal Inp_Level : inout t_aslv16;
signal Ts_Vld : inout std_logic_vector;
signal Ts_Rdy : in std_logic_vector;
signal Ts_Data : inout t_aslv64;
signal Dma_Cmd : in DaqSm2DaqDma_Cmd_t;
signal Dma_Cmd_Vld : in std_logic;
constant Generics_c : Generics_t);
procedure dma_cmd (
signal Clk : in std_logic;
signal StrIrq : in std_logic_vector;
signal Dma_Cmd : in DaqSm2DaqDma_Cmd_t;
signal Dma_Cmd_Vld : in std_logic;
constant Generics_c : Generics_t);
procedure dma_resp (
signal Clk : in std_logic;
signal StrIrq : in std_logic_vector;
signal Dma_Resp : inout DaqDma2DaqSm_Resp_t;
signal Dma_Resp_Vld : inout std_logic;
signal Dma_Resp_Rdy : in std_logic;
signal TfDone : inout std_logic;
constant Generics_c : Generics_t);
procedure ctx (
signal Clk : in std_logic;
signal CtxStr_Cmd : in ToCtxStr_t;
signal CtxStr_Resp : inout FromCtx_t;
signal CtxWin_Cmd : in ToCtxWin_t;
signal CtxWin_Resp : inout FromCtx_t;
constant Generics_c : Generics_t);
end package;
------------------------------------------------------------
-- Package Body
------------------------------------------------------------
package body psi_ms_daq_daq_sm_tb_case_multi_window is
procedure control (
signal Clk : in std_logic;
signal Rst : inout std_logic;
signal GlbEna : inout std_logic;
signal StrEna : inout std_logic_vector;
signal StrIrq : in std_logic_vector;
signal Inp_HasLast : inout std_logic_vector;
signal Inp_Level : inout t_aslv16;
signal Ts_Vld : inout std_logic_vector;
signal Ts_Rdy : in std_logic_vector;
signal Ts_Data : inout t_aslv64;
signal Dma_Cmd : in DaqSm2DaqDma_Cmd_t;
signal Dma_Cmd_Vld : in std_logic;
constant Generics_c : Generics_t) is
begin
print(">> -- multi window --");
-- Linear write with Overwrite
print(">> Linear write with Overwrite");
InitTestCase(Clk, Rst);
TestCase := 0;
ConfigureAuto( WinSize => 4096*2, Ringbuf => '0', Overwrite => '1', Wincnt => 2, Wincur => 0);
Inp_Level(2) <= LvlThreshold_c;
for i in 0 to 6 loop
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
end loop;
Inp_Level(2) <= (others => '0');
ControlWaitCompl(Clk);
-- Ringbuf with overwrite
print(">> Ringbuf with overwrite");
InitTestCase(Clk, Rst);
TestCase := 1;
ConfigureAuto( WinSize => 4096*2, Ringbuf => '1', Overwrite => '1', Wincnt => 2, Wincur => 0);
Inp_Level(2) <= LvlThreshold_c;
for i in 0 to 7 loop
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
end loop;
Inp_Level(2) <= (others => '0');
ControlWaitCompl(Clk);
-- Linear without overwrite, no trigger
print(">> Linear without overwrite, no trigger");
InitTestCase(Clk, Rst);
TestCase := 2;
ConfigureAuto( WinSize => 4096*2, Ringbuf => '0', Overwrite => '0', Wincnt => 2, Wincur => 0);
Inp_Level(2) <= LvlThreshold_c;
for i in 0 to 10 loop
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
end loop;
Inp_Level(2) <= (others => '0');
ControlWaitCompl(Clk);
-- Linear without overwrite, trigger
print(">> Linear without overwrite, trigger");
InitTestCase(Clk, Rst);
TestCase := 3;
ConfigureAuto( WinSize => 4096*2, Ringbuf => '0', Overwrite => '0', Wincnt => 2, Wincur => 0);
Inp_Level(2) <= LvlThreshold_c;
for i in 0 to 5 loop
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
end loop;
Inp_Level(2) <= (others => '0');
ControlWaitCompl(Clk);
-- Ringbuf without overwrite
print(">> Ringbuf without overwrite");
InitTestCase(Clk, Rst);
TestCase := 4;
ConfigureAuto( WinSize => 4096*2, Ringbuf => '1', Overwrite => '0', Wincnt => 2, Wincur => 0);
Inp_Level(2) <= LvlThreshold_c;
for i in 0 to 7 loop
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
end loop;
Inp_Level(2) <= (others => '0');
ControlWaitCompl(Clk);
end procedure;
procedure dma_cmd (
signal Clk : in std_logic;
signal StrIrq : in std_logic_vector;
signal Dma_Cmd : in DaqSm2DaqDma_Cmd_t;
signal Dma_Cmd_Vld : in std_logic;
constant Generics_c : Generics_t) is
begin
-- Linear write with Overwrite
WaitForCase(0, Clk);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, Msg => "Wr0.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, Msg => "Wr0.1", NextWin => true,
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
--> Finished by trigger
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, ExeSize => 512, Msg => "Wr1.0", NextWin => true,
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, Msg => "Wr2.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, Msg => "Wr2.1", NextWin => true,
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
--> Finished by trigger
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, ExeSize => 512, Msg => "Wr3.0", NextWin => true,
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, Msg => "Wr4.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ProcDone(2) := '1';
-- Ringbuf with overwrite
WaitForCase(1, Clk);
-- Win0
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, Msg => "Wr0.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, Msg => "Wr0.1",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, ExeSize => 512, Msg => "Wr0.2", NextWin => true,
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
-- Win1
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, ExeSize => 512, Msg => "Wr1.0", NextWin => true,
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
-- Win2
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, Msg => "Wr2.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, ExeSize => 768, Msg => "Wr2.1", NextWin => true,
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
-- Win 0 (second time)
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, Msg => "Wr3.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, Msg => "Wr3.1",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ProcDone(2) := '1';
-- Linear without overwrite, no trigger
WaitForCase(2, Clk);
for win in 0 to 4 loop
for burst in 0 to 1 loop
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, NextWin => (burst = 1), Msg => "Wr" & to_string(win) & "." & to_string(burst),
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
end loop;
end loop;
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, Msg => "Wr5.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ProcDone(2) := '1';
-- Linear without overwrite, trigger
WaitForCase(3, Clk);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, ExeSize => 512, Msg => "Wr0.0", NextWin => true,
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, Msg => "Wr1.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, Msg => "Wr1.1",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld, NextWin => true);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, ExeSize => 512, Msg => "Wr2.0", NextWin => true,
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, ExeSize => 512, Msg => "Wr3.0", NextWin => true,
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, Msg => "Wr4.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ProcDone(2) := '1';
-- Ringbuf without overwrite
WaitForCase(4, Clk);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, ExeSize => 512, Msg => "Wr0.0", NextWin => true,
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, Msg => "Wr1.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, Msg => "Wr1.1",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, ExeSize => 512, Msg => "Wr1.2", NextWin => true,
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, ExeSize => 512, Msg => "Wr2.0", NextWin => true,
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, Msg => "Wr3.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, ExeSize => 512, Msg => "Wr3.1", NextWin => true,
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, Msg => "Wr4.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ProcDone(2) := '1';
end procedure;
procedure dma_resp (
signal Clk : in std_logic;
signal StrIrq : in std_logic_vector;
signal Dma_Resp : inout DaqDma2DaqSm_Resp_t;
signal Dma_Resp_Vld : inout std_logic;
signal Dma_Resp_Rdy : in std_logic;
signal TfDone : inout std_logic;
constant Generics_c : Generics_t) is
begin
-- Linear write with Overwrite
WaitForCase(0, Clk);
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '1',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '1',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ProcDone(1) := '1';
-- Ringbuf with overwrite
WaitForCase(1, Clk);
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '1',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '1',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '1',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ProcDone(1) := '1';
-- Linear without overwrite, no trigger
WaitForCase(2, Clk);
for win in 0 to 4 loop
for burst in 0 to 1 loop
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
end loop;
end loop;
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ProcDone(1) := '1';
-- Linear without overwrite, trigger
WaitForCase(3, Clk);
ApplyDmaRespAuto( Stream => 2, Trigger => '1',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '1',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '1',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ProcDone(1) := '1';
-- Ringbuf without overwrite
WaitForCase(3, Clk);
ApplyDmaRespAuto( Stream => 2, Trigger => '1',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '1',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '1',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '1',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ProcDone(1) := '1';
end procedure;
procedure ctx (
signal Clk : in std_logic;
signal CtxStr_Cmd : in ToCtxStr_t;
signal CtxStr_Resp : inout FromCtx_t;
signal CtxWin_Cmd : in ToCtxWin_t;
signal CtxWin_Resp : inout FromCtx_t;
constant Generics_c : Generics_t) is
begin
-- Linear write with Overwrite
WaitForCase(0, Clk);
ExpCtxFullBurstAuto( Stream => 2, Msg => "Wr0.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, NextWin => true, Msg => "Wr0.1",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, NextWin => true, IsTrig => true, Msg => "Wr1.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, Msg => "Wr2.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, NextWin => true, Msg => "Wr2.1",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, NextWin => true, IsTrig => true, Msg => "Wr3.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, Msg => "Wr4.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ProcDone(0) := '1';
-- Ringbuf with overwrite
WaitForCase(1, Clk);
ExpCtxFullBurstAuto( Stream => 2, Msg => "Wr0.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, Msg => "Wr0.1",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, NextWin => true, IsTrig => true, Msg => "Wr0.2",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, NextWin => true, IsTrig => true, Msg => "Wr1.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, Msg => "Wr2.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, NextWin => true, IsTrig => true, Msg => "Wr2.1",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, Msg => "Wr3.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, Msg => "Wr3.1",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ProcDone(0) := '1';
-- Linear without overwrite, no trigger
WaitForCase(2, Clk);
for win in 0 to 2 loop
for burst in 0 to 1 loop
ExpCtxFullBurstAuto( Stream => 2, NextWin => (burst=1), Msg => "Wr" & to_string(win) & "." & to_string(burst),
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
end loop;
end loop;
ExpCtxReadAuto( Stream => 2, Msg => "SW not ready 0.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxReadAuto( Stream => 2, Msg => "SW not ready 0.1",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
SplsWinStr_v(2)(0) := 0;
ExpCtxFullBurstAuto( Stream => 2, Msg => "Wr3.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, NextWin => true, Msg => "Wr3.1",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxReadAuto( Stream => 2, Msg => "SW not ready 1.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxReadAuto( Stream => 2, Msg => "SW not ready 1.1",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
SplsWinStr_v(2)(1) := 0;
SplsWinStr_v(2)(2) := 0;
ExpCtxFullBurstAuto( Stream => 2, Msg => "Wr4.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, NextWin => true, Msg => "Wr4.1",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, Msg => "Wr5.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ProcDone(0) := '1';
-- Linear without overwrite, trigger
WaitForCase(3, Clk);
SplsWinStr_v(2) := (others => 4096/4);
ExpCtxReadAuto( Stream => 2, Msg => "SW not ready 0.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
SplsWinStr_v(2)(0 to 2) := (others => 0);
ExpCtxFullBurstAuto( Stream => 2, Msg => "Wr0.0", NextWin => true, IsTrig => true,
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, Msg => "Wr1.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, NextWin => true, Msg => "Wr1.1",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, NextWin => true, IsTrig => true, Msg => "Wr2.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxReadAuto( Stream => 2, Msg => "SW not ready 1.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxReadAuto( Stream => 2, Msg => "SW not ready 1.1",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
SplsWinStr_v(2)(0) := 0;
ExpCtxFullBurstAuto( Stream => 2, NextWin => true, IsTrig => true, Msg => "Wr3.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxReadAuto( Stream => 2, Msg => "SW not ready 2.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxReadAuto( Stream => 2, Msg => "SW not ready 2.1",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
SplsWinStr_v(2)(1) := 0;
ExpCtxFullBurstAuto( Stream => 2, Msg => "Wr4.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ProcDone(0) := '1';
-- Ringbuf without overwrite
WaitForCase(4, Clk);
ExpCtxFullBurstAuto( Stream => 2, Msg => "Wr0.0", NextWin => true, IsTrig => true,
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, Msg => "Wr1.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, Msg => "Wr1.1",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, NextWin => true, IsTrig => true, Msg => "Wr1.2",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, NextWin => true, IsTrig => true, Msg => "Wr2.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxReadAuto( Stream => 2, Msg => "SW not ready 0.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxReadAuto( Stream => 2, Msg => "SW not ready 0.1",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
SplsWinStr_v(2)(0) := 0;
ExpCtxFullBurstAuto( Stream => 2, Msg => "Wr3.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, NextWin => true, IsTrig => true, Msg => "Wr3.1",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxReadAuto( Stream => 2, Msg => "SW not ready 1.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
SplsWinStr_v(2)(1) := 0;
ExpCtxFullBurstAuto( Stream => 2, Msg => "Wr4.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ProcDone(0) := '1';
end procedure;
end;

View File

@@ -1,308 +0,0 @@
------------------------------------------------------------
-- Libraries
------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_common_array_pkg.all;
use work.psi_ms_daq_pkg.all;
library work;
use work.psi_ms_daq_daq_sm_tb_pkg.all;
library work;
use work.psi_tb_txt_util.all;
use work.psi_tb_compare_pkg.all;
use work.psi_common_array_pkg.all;
------------------------------------------------------------
-- Package Header
------------------------------------------------------------
package psi_ms_daq_daq_sm_tb_case_priorities is
procedure control (
signal Clk : in std_logic;
signal Rst : inout std_logic;
signal GlbEna : inout std_logic;
signal StrEna : inout std_logic_vector;
signal StrIrq : in std_logic_vector;
signal Inp_HasLast : inout std_logic_vector;
signal Inp_Level : inout t_aslv16;
signal Ts_Vld : inout std_logic_vector;
signal Ts_Rdy : in std_logic_vector;
signal Ts_Data : inout t_aslv64;
signal Dma_Cmd : in DaqSm2DaqDma_Cmd_t;
signal Dma_Cmd_Vld : in std_logic;
constant Generics_c : Generics_t);
procedure dma_cmd (
signal Clk : in std_logic;
signal StrIrq : in std_logic_vector;
signal Dma_Cmd : in DaqSm2DaqDma_Cmd_t;
signal Dma_Cmd_Vld : in std_logic;
constant Generics_c : Generics_t);
procedure dma_resp (
signal Clk : in std_logic;
signal StrIrq : in std_logic_vector;
signal Dma_Resp : inout DaqDma2DaqSm_Resp_t;
signal Dma_Resp_Vld : inout std_logic;
signal Dma_Resp_Rdy : in std_logic;
signal TfDone : inout std_logic;
constant Generics_c : Generics_t);
procedure ctx (
signal Clk : in std_logic;
signal CtxStr_Cmd : in ToCtxStr_t;
signal CtxStr_Resp : inout FromCtx_t;
signal CtxWin_Cmd : in ToCtxWin_t;
signal CtxWin_Resp : inout FromCtx_t;
constant Generics_c : Generics_t);
constant StreamOrder_c : t_ainteger := (3, 0, 1, 2);
end package;
------------------------------------------------------------
-- Package Body
------------------------------------------------------------
package body psi_ms_daq_daq_sm_tb_case_priorities is
procedure control (
signal Clk : in std_logic;
signal Rst : inout std_logic;
signal GlbEna : inout std_logic;
signal StrEna : inout std_logic_vector;
signal StrIrq : in std_logic_vector;
signal Inp_HasLast : inout std_logic_vector;
signal Inp_Level : inout t_aslv16;
signal Ts_Vld : inout std_logic_vector;
signal Ts_Rdy : in std_logic_vector;
signal Ts_Data : inout t_aslv64;
signal Dma_Cmd : in DaqSm2DaqDma_Cmd_t;
signal Dma_Cmd_Vld : in std_logic;
constant Generics_c : Generics_t) is
begin
print(">> -- priorities --");
-- Check correct order on parallel assertion
InitTestCase(Clk, Rst);
print(">> Check correct order on parallel assertion");
TestCase := 0;
for i in 0 to 3 loop
Inp_Level(i) <= std_logic_vector(to_unsigned(Size4k_c/DataWidthBytes_c, Inp_Level(i)'length));
end loop;
for i in 0 to 3 loop
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
Inp_Level(Dma_Cmd.Stream) <= (others => '0');
end loop;
ControlWaitCompl(Clk);
-- Round Robin behavior
InitTestCase(Clk, Rst);
print(">> Round Robin behavior");
TestCase := 1;
Inp_Level(0) <= std_logic_vector(to_unsigned(Size4k_c/DataWidthBytes_c, Inp_Level(0)'length));
Inp_Level(3) <= std_logic_vector(to_unsigned(Size4k_c/DataWidthBytes_c, Inp_Level(3)'length));
Inp_Level(1) <= std_logic_vector(to_unsigned(Size4k_c/DataWidthBytes_c, Inp_Level(1)'length));
for i in 0 to 3 loop
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
end loop;
Inp_Level(0) <= (others => '0');
Inp_Level(3) <= (others => '0');
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
Inp_Level(1) <= (others => '0');
ControlWaitCompl(Clk);
-- Reassertion of high-priority streams
InitTestCase(Clk, Rst);
print(">> Reassertion of high-priority streams");
TestCase := 2;
Inp_Level(0) <= std_logic_vector(to_unsigned(Size4k_c/DataWidthBytes_c, Inp_Level(0)'length));
Inp_Level(1) <= std_logic_vector(to_unsigned(Size4k_c/DataWidthBytes_c, Inp_Level(1)'length));
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
Inp_Level(0) <= (others => '0');
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
Inp_Level(0) <= std_logic_vector(to_unsigned(Size4k_c/DataWidthBytes_c, Inp_Level(0)'length));
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
Inp_Level(0) <= (others => '0');
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
Inp_Level(1) <= (others => '0');
ControlWaitCompl(Clk);
FinishTestCase;
end procedure;
procedure dma_cmd (
signal Clk : in std_logic;
signal StrIrq : in std_logic_vector;
signal Dma_Cmd : in DaqSm2DaqDma_Cmd_t;
signal Dma_Cmd_Vld : in std_logic;
constant Generics_c : Generics_t) is
variable Stream_v : integer;
begin
-- Check correct order on parallel assertion
WaitForCase(0, Clk);
for i in 0 to 3 loop
ExpectDmaCmdAuto( Stream => StreamOrder_c(i), MaxSize => Size4k_c,
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
end loop;
ProcDone(2) := '1';
-- Round Robin behavior
WaitForCase(1, Clk);
for i in 0 to 1 loop
for s in 0 to 1 loop
ExpectDmaCmdAuto( Stream => choose(s=0, 3, 0), MaxSize => Size4k_c, Msg => "i=" & to_string(i) & ", s=" & to_string(s),
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
end loop;
end loop;
ExpectDmaCmdAuto( Stream => 1, MaxSize => Size4k_c,
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ProcDone(2) := '1';
-- Reassertion of high-priority streams
WaitForCase(2, Clk);
ExpectDmaCmdAuto( Stream => 0, MaxSize => Size4k_c, Msg => "HP0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 1, MaxSize => Size4k_c, Msg => "LP0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 0, MaxSize => Size4k_c, Msg => "HP1",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 1, MaxSize => Size4k_c, Msg => "LP1",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ProcDone(2) := '1';
end procedure;
procedure dma_resp (
signal Clk : in std_logic;
signal StrIrq : in std_logic_vector;
signal Dma_Resp : inout DaqDma2DaqSm_Resp_t;
signal Dma_Resp_Vld : inout std_logic;
signal Dma_Resp_Rdy : in std_logic;
signal TfDone : inout std_logic;
constant Generics_c : Generics_t) is
variable Stream_v : integer;
begin
-- Check correct order on parallel assertion
WaitForCase(0, Clk);
for i in 0 to 3 loop
ApplyDmaResp( Stream => StreamOrder_c(i), Size => Size4k_c, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
end loop;
ProcDone(1) := '1';
-- Round Robin behavior
WaitForCase(1, Clk);
for i in 0 to 1 loop
for s in 0 to 1 loop
ApplyDmaResp( Stream => choose(s=0, 3, 0), Size => Size4k_c, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
end loop;
end loop;
ApplyDmaResp( Stream => 1, Size => Size4k_c, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ProcDone(1) := '1';
-- Reassertion of high-priority streams
WaitForCase(2, Clk);
ApplyDmaResp( Stream => 0, Size => Size4k_c, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaResp( Stream => 1, Size => Size4k_c, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaResp( Stream => 0, Size => Size4k_c, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaResp( Stream => 1, Size => Size4k_c, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ProcDone(1) := '1';
end procedure;
procedure ctx (
signal Clk : in std_logic;
signal CtxStr_Cmd : in ToCtxStr_t;
signal CtxStr_Resp : inout FromCtx_t;
signal CtxWin_Cmd : in ToCtxWin_t;
signal CtxWin_Resp : inout FromCtx_t;
constant Generics_c : Generics_t) is
variable Ptr_v : integer;
variable Stream_v : integer;
variable PtrStr_v : t_ainteger(0 to 3);
variable SplsStr_v : t_ainteger(0 to 3) := (others => 0);
begin
-- Check two 4k Transfers in a row on stream 0
WaitForCase(0, Clk);
-- Requests are handled before responses
for i in 0 to 3 loop
ExpCtxReadAuto( Stream => StreamOrder_c(i),
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
end loop;
for i in 0 to 3 loop
ExpCtxUpdateAuto( Stream => StreamOrder_c(i),
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
end loop;
ProcDone(0) := '1';
-- Round Robin behavior
WaitForCase(1, Clk);
PtrStr_v := (16#00000#, 16#10000#, 16#20000#, 16#30000#);
-- First high prio command
ExpCtxReadAuto( Stream => 3,
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
-- Second high prio stream can immediately send the next command
ExpCtxReadAuto( Stream => 0,
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
-- Wait for response and schnedule next high prio command
ExpCtxUpdateAuto( Stream => 3,
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxReadAuto( Stream => 3,
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
-- Wait for response and schnedule next high prio command
ExpCtxUpdateAuto( Stream => 0,
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxReadAuto( Stream => 0,
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
-- No more high prio data, so low prio command follows
ExpCtxReadAuto( Stream => 1,
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
-- pending responses
ExpCtxUpdateAuto( Stream => 3, Msg => "RobinLast3",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxUpdateAuto( Stream => 0, Msg => "RobinLast0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxUpdateAuto( Stream => 1, Msg => "RobinLast1",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ProcDone(0) := '1';
-- Reassertion of high-priority streams
WaitForCase(2, Clk);
-- Start high-prio transfer
ExpCtxReadAuto( Stream => 0, Msg => "Start HP0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
-- Start low-prio transfer
ExpCtxReadAuto( Stream => 1, Msg => "Start LP0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
-- High-prio data available, so wait for high-prio response and restart transfer
ExpCtxUpdateAuto( Stream => 0, Msg => "Finish HP0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxReadAuto( Stream => 0, Msg => "Start HP1",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
-- Low-prio data available, so wait for high-prio response and restart transfer
ExpCtxUpdateAuto( Stream => 1, Msg => "Finish LP0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxReadAuto( Stream => 1, Msg => "Start LP1",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
-- Completion of last high prio transfer
ExpCtxUpdateAuto( Stream => 0, Msg => "Finish HP1",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
-- Completion of last low prio transfer
ExpCtxUpdateAuto( Stream => 1, Msg => "Finish LP1",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ProcDone(0) := '1';
end procedure;
end;

View File

@@ -1,546 +0,0 @@
------------------------------------------------------------
-- Libraries
------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_common_array_pkg.all;
use work.psi_ms_daq_pkg.all;
library work;
use work.psi_ms_daq_daq_sm_tb_pkg.all;
library work;
use work.psi_tb_txt_util.all;
use work.psi_tb_compare_pkg.all;
------------------------------------------------------------
-- Package Header
------------------------------------------------------------
package psi_ms_daq_daq_sm_tb_case_single_simple is
procedure control (
signal Clk : in std_logic;
signal Rst : inout std_logic;
signal GlbEna : inout std_logic;
signal StrEna : inout std_logic_vector;
signal StrIrq : in std_logic_vector;
signal Inp_HasLast : inout std_logic_vector;
signal Inp_Level : inout t_aslv16;
signal Ts_Vld : inout std_logic_vector;
signal Ts_Rdy : in std_logic_vector;
signal Ts_Data : inout t_aslv64;
signal Dma_Cmd : in DaqSm2DaqDma_Cmd_t;
signal Dma_Cmd_Vld : in std_logic;
constant Generics_c : Generics_t);
procedure dma_cmd (
signal Clk : in std_logic;
signal StrIrq : in std_logic_vector;
signal Dma_Cmd : in DaqSm2DaqDma_Cmd_t;
signal Dma_Cmd_Vld : in std_logic;
constant Generics_c : Generics_t);
procedure dma_resp (
signal Clk : in std_logic;
signal StrIrq : in std_logic_vector;
signal Dma_Resp : inout DaqDma2DaqSm_Resp_t;
signal Dma_Resp_Vld : inout std_logic;
signal Dma_Resp_Rdy : in std_logic;
signal TfDone : inout std_logic;
constant Generics_c : Generics_t);
procedure ctx (
signal Clk : in std_logic;
signal CtxStr_Cmd : in ToCtxStr_t;
signal CtxStr_Resp : inout FromCtx_t;
signal CtxWin_Cmd : in ToCtxWin_t;
signal CtxWin_Resp : inout FromCtx_t;
constant Generics_c : Generics_t);
end package;
------------------------------------------------------------
-- Package Body
------------------------------------------------------------
package body psi_ms_daq_daq_sm_tb_case_single_simple is
procedure control (
signal Clk : in std_logic;
signal Rst : inout std_logic;
signal GlbEna : inout std_logic;
signal StrEna : inout std_logic_vector;
signal StrIrq : in std_logic_vector;
signal Inp_HasLast : inout std_logic_vector;
signal Inp_Level : inout t_aslv16;
signal Ts_Vld : inout std_logic_vector;
signal Ts_Rdy : in std_logic_vector;
signal Ts_Data : inout t_aslv64;
signal Dma_Cmd : in DaqSm2DaqDma_Cmd_t;
signal Dma_Cmd_Vld : in std_logic;
constant Generics_c : Generics_t) is
variable StartTime_v : time;
begin
print(">> -- single_simple --");
InitTestCase(Clk, Rst);
-- Check Steady behavior
print(">> Check Steady Behavior");
TestCase := 0;
StartTime_v := now;
while now < StartTime_v + 1 us loop
StdlvCompareInt(0, Ts_Rdy, "Ts_Rdy high in steady check");
wait until rising_edge(Clk);
end loop;
ControlWaitCompl(Clk);
-- No reaction on insignificant leven
print(">> No reaction on insignificant leven");
TestCase := 1;
StartTime_v := now;
while now < StartTime_v + 1 us loop
StdlvCompareInt(0, Ts_Rdy, "Ts_Rdy high in steady check");
wait until rising_edge(Clk);
end loop;
ControlWaitCompl(Clk);
-- First transfer after startup, 4k Aligned
-- .. This is required to bypass all special handling for the first transfer after enabling a stream.
print(">> First transfer after startup, 4k Aligned");
TestCase := 2;
for str in 0 to 3 loop
Inp_Level(str) <= std_logic_vector(to_unsigned(Size4k_c/DataWidthBytes_c, Inp_Level(str)'length));
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
Inp_Level(str) <= (others => '0');
wait for 1 us;
end loop;
ControlWaitCompl(Clk);
-- Check a single 4k aligned burst on stream 1
print(">> most simple 4k Aligned transfer");
TestCase := 3;
Inp_Level(1) <= std_logic_vector(to_unsigned(Size4k_c/DataWidthBytes_c, Inp_Level(0)'length));
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
Inp_Level(1) <= (others => '0');
ControlWaitCompl(Clk);
-- Check two 4k Transfers in a row on stream 0
print(">> two 4k Aligned transfers");
TestCase := 4;
Inp_Level(0) <= std_logic_vector(to_unsigned(Size4k_c/DataWidthBytes_c, Inp_Level(0)'length));
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
Inp_Level(0) <= (others => '0');
ControlWaitCompl(Clk);
-- Check maximum Transfer size limitation
print(">> Transfer size limitation to 4k");
TestCase := 5;
Inp_Level(0) <= std_logic_vector(to_unsigned(Size4k_c*2/DataWidthBytes_c, Inp_Level(0)'length));
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
Inp_Level(0) <= (others => '0');
ControlWaitCompl(Clk);
-- Check 4k boundary limitation
print(">> Check 4k boundary limitation");
TestCase := 6;
Inp_Level(0) <= std_logic_vector(to_unsigned(Size4k_c/DataWidthBytes_c, Inp_Level(0)'length));
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
Inp_Level(0) <= (others => '0');
ControlWaitCompl(Clk);
-- Check window size limitation
print(">> Check window size limitation");
TestCase := 7;
Inp_Level(1) <= std_logic_vector(to_unsigned(Size4k_c/DataWidthBytes_c, Inp_Level(0)'length));
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
Inp_Level(1) <= (others => '0');
ControlWaitCompl(Clk);
-- check response smaller than request
print(">> check response smaller than request");
TestCase := 8;
Inp_Level(1) <= std_logic_vector(to_unsigned(Size4k_c/DataWidthBytes_c, Inp_Level(0)'length));
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
Inp_Level(1) <= (others => '0');
ControlWaitCompl(Clk);
FinishTestCase;
end procedure;
procedure dma_cmd (
signal Clk : in std_logic;
signal StrIrq : in std_logic_vector;
signal Dma_Cmd : in DaqSm2DaqDma_Cmd_t;
signal Dma_Cmd_Vld : in std_logic;
constant Generics_c : Generics_t) is
variable StartTime_v : time;
begin
-- Check Steady behavior
WaitForCase(0, Clk);
StartTime_v := now;
while now < StartTime_v + 1 us loop
StdlCompare(0, Dma_Cmd_Vld, "Dma_Cmd_Vld high in steady check");
wait until rising_edge(Clk);
end loop;
ProcDone(2) := '1';
-- No reaction on insignificant level
WaitForCase(1, Clk);
StartTime_v := now;
while now < StartTime_v + 1 us loop
StdlCompare(0, Dma_Cmd_Vld, "Dma_Cmd_Vld high in insignificant level");
wait until rising_edge(Clk);
end loop;
ProcDone(2) := '1';
-- First transfer after startup, 4k Aligned
WaitForCase(2, Clk);
for str in 0 to 3 loop
ExpectDmaCmd( Stream => str,
Address => 16#01230000#,
MaxSize => Size4k_c,
Clk => Clk,
Dma_Cmd => Dma_Cmd,
Dma_Vld => Dma_Cmd_Vld);
end loop;
ProcDone(2) := '1';
-- Check a single 4k aligned burst on stream 1
WaitForCase(3, Clk);
ExpectDmaCmd( Stream => 1,
Address => 16#01238000#,
MaxSize => Size4k_c,
Clk => Clk,
Dma_Cmd => Dma_Cmd,
Dma_Vld => Dma_Cmd_Vld);
ProcDone(2) := '1';
-- Check two 4k Transfers in a row on stream 0
WaitForCase(4, Clk);
for i in 0 to 1 loop
ExpectDmaCmd( Stream => 0,
Address => 16#01238000# + i*16#1000#,
MaxSize => Size4k_c,
Clk => Clk,
Dma_Cmd => Dma_Cmd,
Dma_Vld => Dma_Cmd_Vld,
Msg => "Tf" & to_string(i));
end loop;
ProcDone(2) := '1';
-- Check maximum Transfer size limitation
WaitForCase(5, Clk);
ExpectDmaCmd( Stream => 0,
Address => 16#01238000#,
MaxSize => Size4k_c,
Clk => Clk,
Dma_Cmd => Dma_Cmd,
Dma_Vld => Dma_Cmd_Vld);
ProcDone(2) := '1';
-- Check 4k boundary limitation
WaitForCase(6, Clk);
ExpectDmaCmd( Stream => 0,
Address => 16#01238000#+384,
MaxSize => Size4k_c-384,
Clk => Clk,
Dma_Cmd => Dma_Cmd,
Dma_Vld => Dma_Cmd_Vld);
ProcDone(2) := '1';
-- Check window size limitation
WaitForCase(7, Clk);
ExpectDmaCmd( Stream => 1,
Address => 16#01230000#,
MaxSize => 502,
Clk => Clk,
Dma_Cmd => Dma_Cmd,
Dma_Vld => Dma_Cmd_Vld);
ProcDone(2) := '1';
-- check response smaller than request
WaitForCase(8, Clk);
ExpectDmaCmd( Stream => 1,
Address => 16#01230000#,
MaxSize => Size4k_c,
Clk => Clk,
Dma_Cmd => Dma_Cmd,
Dma_Vld => Dma_Cmd_Vld);
ProcDone(2) := '1';
end procedure;
procedure dma_resp (
signal Clk : in std_logic;
signal StrIrq : in std_logic_vector;
signal Dma_Resp : inout DaqDma2DaqSm_Resp_t;
signal Dma_Resp_Vld : inout std_logic;
signal Dma_Resp_Rdy : in std_logic;
signal TfDone : inout std_logic;
constant Generics_c : Generics_t) is
variable StartTime_v : time;
begin
-- Check Steady behavior
WaitForCase(0, Clk);
StartTime_v := now;
while now < StartTime_v + 1 us loop
StdlCompare(0, Dma_Resp_Rdy, "Dma_Resp_Rdy high in steady check");
wait until rising_edge(Clk);
end loop;
ProcDone(1) := '1';
-- No reaction on insignificant level
WaitForCase(1, Clk);
StartTime_v := now;
while now < StartTime_v + 1 us loop
StdlCompare(0, Dma_Resp_Rdy, "Dma_Resp_Rdy high in insignificant level");
wait until rising_edge(Clk);
end loop;
ProcDone(1) := '1';
-- First transfer after startup, 4k Aligned
WaitForCase(2, Clk);
for str in 0 to 3 loop
ApplyDmaResp( Stream => str,
Size => Size4k_c,
Trigger => '0',
Delay => 200 ns,
Clk => Clk,
Dma_Resp => Dma_Resp,
Dma_Resp_Vld => Dma_Resp_Vld,
Dma_Resp_Rdy => Dma_Resp_Rdy);
end loop;
ProcDone(1) := '1';
-- Check a single 4k aligned burst on stream 1
WaitForCase(3, Clk);
ApplyDmaResp( Stream => 1,
Size => Size4k_c,
Trigger => '0',
Delay => 200 ns,
Clk => Clk,
Dma_Resp => Dma_Resp,
Dma_Resp_Vld => Dma_Resp_Vld,
Dma_Resp_Rdy => Dma_Resp_Rdy);
ProcDone(1) := '1';
-- Check two 4k Transfers in a row on stream 0
WaitForCase(4, Clk);
for i in 0 to 1 loop
ApplyDmaResp( Stream => 0,
Size => Size4k_c,
Trigger => '0',
Delay => 0 ns,
Clk => Clk,
Dma_Resp => Dma_Resp,
Dma_Resp_Vld => Dma_Resp_Vld,
Dma_Resp_Rdy => Dma_Resp_Rdy,
Msg => "Tf" & to_string(i));
end loop;
ProcDone(1) := '1';
-- Check maximum Transfer size limitation
WaitForCase(5, Clk);
ApplyDmaResp( Stream => 0,
Size => Size4k_c,
Trigger => '0',
Clk => Clk,
Dma_Resp => Dma_Resp,
Dma_Resp_Vld => Dma_Resp_Vld,
Dma_Resp_Rdy => Dma_Resp_Rdy);
ProcDone(1) := '1';
-- Check 4k boundary limitation
WaitForCase(6, Clk);
ApplyDmaResp( Stream => 0,
Size => Size4k_c-384,
Trigger => '0',
Clk => Clk,
Dma_Resp => Dma_Resp,
Dma_Resp_Vld => Dma_Resp_Vld,
Dma_Resp_Rdy => Dma_Resp_Rdy);
ProcDone(1) := '1';
-- Check window size limitation
WaitForCase(7, Clk);
ApplyDmaResp( Stream => 1,
Size => 502,
Trigger => '0',
Clk => Clk,
Dma_Resp => Dma_Resp,
Dma_Resp_Vld => Dma_Resp_Vld,
Dma_Resp_Rdy => Dma_Resp_Rdy);
ProcDone(1) := '1';
-- check response smaller than request
WaitForCase(8, Clk);
ApplyDmaResp( Stream => 1,
Size => 500,
Trigger => '0',
Clk => Clk,
Dma_Resp => Dma_Resp,
Dma_Resp_Vld => Dma_Resp_Vld,
Dma_Resp_Rdy => Dma_Resp_Rdy);
ProcDone(1) := '1';
end procedure;
procedure ctx (
signal Clk : in std_logic;
signal CtxStr_Cmd : in ToCtxStr_t;
signal CtxStr_Resp : inout FromCtx_t;
signal CtxWin_Cmd : in ToCtxWin_t;
signal CtxWin_Resp : inout FromCtx_t;
constant Generics_c : Generics_t) is
variable StartTime_v : time;
variable PtrStr1_v : integer;
begin
-- Check Steady behavior
WaitForCase(0, Clk);
StartTime_v := now;
while now < StartTime_v + 1 us loop
StdlCompare(0, CtxStr_Cmd.WenLo, "CtxStr_Cmd.WenLo high in steady check");
StdlCompare(0, CtxStr_Cmd.WenHi, "CtxStr_Cmd.WenHi high in steady check");
StdlCompare(0, CtxWin_Cmd.WenLo, "CtxWin_Cmd.WenLo high in steady check");
StdlCompare(0, CtxWin_Cmd.WenHi, "CtxWin_Cmd.WenHi high in steady check");
wait until rising_edge(Clk);
end loop;
ProcDone(0) := '1';
-- No reaction on insignificant leven
WaitForCase(1, Clk);
StartTime_v := now;
while now < StartTime_v + 1 us loop
StdlCompare(0, CtxStr_Cmd.WenLo, "CtxStr_Cmd.WenLo high in insignificant level");
StdlCompare(0, CtxStr_Cmd.WenHi, "CtxStr_Cmd.WenHi high in insignificant level");
StdlCompare(0, CtxWin_Cmd.WenLo, "CtxWin_Cmd.WenLo high in insignificant level");
StdlCompare(0, CtxWin_Cmd.WenHi, "CtxWin_Cmd.WenHi high in insignificant level");
wait until rising_edge(Clk);
end loop;
ProcDone(0) := '1';
-- First transfer after startup, 4k Aligned
WaitForCase(2, Clk);
for str in 0 to 3 loop
PtrStr1_v := 16#01230000#;
ExpCtxFullBurst( Stream => str,
TfSize => Size4k_c,
PtrBefore => PtrStr1_v,
SamplesWinBefore => 0,
PtrAfter => PtrStr1_v,
Clk => Clk,
CtxStr_Cmd => CtxStr_Cmd,
CtxStr_Resp => CtxStr_Resp,
CtxWin_Cmd => CtxWin_Cmd,
CtxWin_Resp => CtxWin_Resp,
Msg => "Str" & to_string(str));
end loop;
ProcDone(0) := '1';
-- Check a single 4k aligned burst on stream 1
WaitForCase(3, Clk);
PtrStr1_v := 16#01238000#;
ExpCtxFullBurst( Stream => 1,
TfSize => Size4k_c,
PtrBefore => PtrStr1_v,
SamplesWinBefore => 0,
PtrAfter => PtrStr1_v,
Clk => Clk,
CtxStr_Cmd => CtxStr_Cmd,
CtxStr_Resp => CtxStr_Resp,
CtxWin_Cmd => CtxWin_Cmd,
CtxWin_Resp => CtxWin_Resp);
ProcDone(0) := '1';
-- Check two 4k Transfers in a row on stream 0
WaitForCase(4, Clk);
PtrStr1_v := 16#01238000#;
for i in 0 to 1 loop
ExpCtxFullBurst( Stream => 0,
TfSize => Size4k_c,
PtrBefore => PtrStr1_v,
SamplesWinBefore => 0,
PtrAfter => PtrStr1_v,
Clk => Clk,
CtxStr_Cmd => CtxStr_Cmd,
CtxStr_Resp => CtxStr_Resp,
CtxWin_Cmd => CtxWin_Cmd,
CtxWin_Resp => CtxWin_Resp);
end loop;
ProcDone(0) := '1';
-- Check maximum Transfer size limitation
WaitForCase(5, Clk);
PtrStr1_v := 16#01238000#;
ExpCtxFullBurst( Stream => 0,
TfSize => Size4k_c,
PtrBefore => PtrStr1_v,
SamplesWinBefore => 0,
PtrAfter => PtrStr1_v,
Clk => Clk,
CtxStr_Cmd => CtxStr_Cmd,
CtxStr_Resp => CtxStr_Resp,
CtxWin_Cmd => CtxWin_Cmd,
CtxWin_Resp => CtxWin_Resp);
ProcDone(0) := '1';
-- Check 4k boundary limitation
WaitForCase(6, Clk);
PtrStr1_v := 16#01238000#+384;
ExpCtxFullBurst( Stream => 0,
TfSize => Size4k_c-384,
PtrBefore => PtrStr1_v,
SamplesWinBefore => 0,
PtrAfter => PtrStr1_v,
Clk => Clk,
CtxStr_Cmd => CtxStr_Cmd,
CtxStr_Resp => CtxStr_Resp,
CtxWin_Cmd => CtxWin_Cmd,
CtxWin_Resp => CtxWin_Resp);
assert PtrStr1_v = 16#01239000# report "###ERROR###: Unexpected pointer value after transfer" severity error;
ProcDone(0) := '1';
-- Check window size limitation
WaitForCase(7, Clk);
PtrStr1_v := 16#01230000#;
ExpCtxFullBurst( Stream => 1,
BufStart => 16#01230000#,
TfSize => 502,
NextWin => true,
WinSize => 502,
PtrBefore => PtrStr1_v,
SamplesWinBefore => 0,
PtrAfter => PtrStr1_v,
Clk => Clk,
CtxStr_Cmd => CtxStr_Cmd,
CtxStr_Resp => CtxStr_Resp,
CtxWin_Cmd => CtxWin_Cmd,
CtxWin_Resp => CtxWin_Resp);
ProcDone(0) := '1';
-- check response smaller than request
WaitForCase(8, Clk);
PtrStr1_v := 16#01230000#;
ExpCtxFullBurst( Stream => 1,
BufStart => 16#01230000#,
TfSize => 500,
PtrBefore => PtrStr1_v,
SamplesWinBefore => 0,
PtrAfter => PtrStr1_v,
Clk => Clk,
CtxStr_Cmd => CtxStr_Cmd,
CtxStr_Resp => CtxStr_Resp,
CtxWin_Cmd => CtxWin_Cmd,
CtxWin_Resp => CtxWin_Resp);
assert PtrStr1_v = 16#01230000#+500 report "###ERROR###: Unexpected pointer value after transfer" severity error;
ProcDone(0) := '1';
end procedure;
end;

View File

@@ -1,398 +0,0 @@
------------------------------------------------------------
-- Libraries
------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_common_array_pkg.all;
use work.psi_ms_daq_pkg.all;
library work;
use work.psi_ms_daq_daq_sm_tb_pkg.all;
library work;
use work.psi_tb_txt_util.all;
use work.psi_tb_compare_pkg.all;
------------------------------------------------------------
-- Package Header
------------------------------------------------------------
package psi_ms_daq_daq_sm_tb_case_single_window is
procedure control (
signal Clk : in std_logic;
signal Rst : inout std_logic;
signal GlbEna : inout std_logic;
signal StrEna : inout std_logic_vector;
signal StrIrq : in std_logic_vector;
signal Inp_HasLast : inout std_logic_vector;
signal Inp_Level : inout t_aslv16;
signal Ts_Vld : inout std_logic_vector;
signal Ts_Rdy : in std_logic_vector;
signal Ts_Data : inout t_aslv64;
signal Dma_Cmd : in DaqSm2DaqDma_Cmd_t;
signal Dma_Cmd_Vld : in std_logic;
constant Generics_c : Generics_t);
procedure dma_cmd (
signal Clk : in std_logic;
signal StrIrq : in std_logic_vector;
signal Dma_Cmd : in DaqSm2DaqDma_Cmd_t;
signal Dma_Cmd_Vld : in std_logic;
constant Generics_c : Generics_t);
procedure dma_resp (
signal Clk : in std_logic;
signal StrIrq : in std_logic_vector;
signal Dma_Resp : inout DaqDma2DaqSm_Resp_t;
signal Dma_Resp_Vld : inout std_logic;
signal Dma_Resp_Rdy : in std_logic;
signal TfDone : inout std_logic;
constant Generics_c : Generics_t);
procedure ctx (
signal Clk : in std_logic;
signal CtxStr_Cmd : in ToCtxStr_t;
signal CtxStr_Resp : inout FromCtx_t;
signal CtxWin_Cmd : in ToCtxWin_t;
signal CtxWin_Resp : inout FromCtx_t;
constant Generics_c : Generics_t);
end package;
------------------------------------------------------------
-- Package Body
------------------------------------------------------------
package body psi_ms_daq_daq_sm_tb_case_single_window is
procedure control (
signal Clk : in std_logic;
signal Rst : inout std_logic;
signal GlbEna : inout std_logic;
signal StrEna : inout std_logic_vector;
signal StrIrq : in std_logic_vector;
signal Inp_HasLast : inout std_logic_vector;
signal Inp_Level : inout t_aslv16;
signal Ts_Vld : inout std_logic_vector;
signal Ts_Rdy : in std_logic_vector;
signal Ts_Data : inout t_aslv64;
signal Dma_Cmd : in DaqSm2DaqDma_Cmd_t;
signal Dma_Cmd_Vld : in std_logic;
constant Generics_c : Generics_t) is
begin
print(">> -- single window --");
-- Linear write with Overwrite
print(">> Linear write with Overwrite");
InitTestCase(Clk, Rst);
TestCase := 0;
ConfigureAuto( WinSize => 4096+128, Ringbuf => '0', Overwrite => '1', Wincnt => 0, Wincur => 0);
Inp_Level(2) <= LvlThreshold_c;
for i in 0 to 5 loop
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
end loop;
Inp_Level(2) <= (others => '0');
ControlWaitCompl(Clk);
-- Ringbuf with overwrite
print(">> Ringbuf with overwrite");
InitTestCase(Clk, Rst);
TestCase := 1;
ConfigureAuto( WinSize => 4096+128, Ringbuf => '1', Overwrite => '1', Wincnt => 0, Wincur => 0);
Inp_Level(2) <= LvlThreshold_c;
for i in 0 to 5 loop
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
end loop;
Inp_Level(2) <= (others => '0');
ControlWaitCompl(Clk);
-- Linear without overwrite, no trigger
print(">> Linear without overwrite, no trigger");
InitTestCase(Clk, Rst);
TestCase := 2;
ConfigureAuto( WinSize => 4096+128, Ringbuf => '0', Overwrite => '0', Wincnt => 0, Wincur => 0);
Inp_Level(2) <= LvlThreshold_c;
for i in 0 to 2 loop
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
end loop;
Inp_Level(2) <= (others => '0');
ControlWaitCompl(Clk);
-- Linear without overwrite, trigger
print(">> Linear without overwrite, trigger");
InitTestCase(Clk, Rst);
TestCase := 3;
ConfigureAuto( WinSize => 4096+128, Ringbuf => '0', Overwrite => '0', Wincnt => 0, Wincur => 0);
Inp_Level(2) <= LvlThreshold_c;
for i in 0 to 1 loop
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
end loop;
Inp_Level(2) <= (others => '0');
ControlWaitCompl(Clk);
-- Ringbuf without overwrite
print(">> Ringbuf without overwrite");
wait for 1 us;
InitTestCase(Clk, Rst);
TestCase := 4;
ConfigureAuto( WinSize => 4096+128, Ringbuf => '1', Overwrite => '0', Wincnt => 0, Wincur => 0);
Inp_Level(2) <= LvlThreshold_c;
for i in 0 to 3 loop
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
end loop;
Inp_Level(2) <= (others => '0');
ControlWaitCompl(Clk);
end procedure;
procedure dma_cmd (
signal Clk : in std_logic;
signal StrIrq : in std_logic_vector;
signal Dma_Cmd : in DaqSm2DaqDma_Cmd_t;
signal Dma_Cmd_Vld : in std_logic;
constant Generics_c : Generics_t) is
begin
-- Linear write with Overwrite
WaitForCase(0, Clk);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, Msg => "Wr0.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 128, Msg => "Wr0.1", NextWin => true,
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, Msg => "Wr1.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 128, Msg => "Wr1.1", NextWin => true,
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
PtrDma_v(2) := BufStart_c(2);
--> Finished by trigger
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, ExeSize => 512, Msg => "Wr2.0", NextWin => true,
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
--> Next window on trigger
PtrDma_v(2) := BufStart_c(2);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, Msg => "Wr3.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ProcDone(2) := '1';
-- Ringbuf with overwrite
WaitForCase(1, Clk);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, Msg => "Wr0.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 128, Msg => "Wr0.1", NextWin => true,
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, Msg => "Wr1.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 128, Msg => "Wr1.1", NextWin => true,
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
PtrDma_v(2) := BufStart_c(2);
--> Finished by trigger
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, ExeSize => 512, Msg => "Wr2.0", NextWin => true,
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
--> Next window on trigger
PtrDma_v(2) := BufStart_c(2);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, Msg => "Wr3.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ProcDone(2) := '1';
-- Linear without overwrite, no trigger
WaitForCase(2, Clk);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, Msg => "Wr0.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 128, Msg => "Wr0.1", NextWin => true,
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, Msg => "Wr1.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ProcDone(2) := '1';
-- Linear without overwrite, trigger
WaitForCase(3, Clk);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, ExeSize => 4000, Msg => "Wr0.0", NextWin => true,
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, Msg => "Wr1.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ProcDone(2) := '1';
-- Ringbuf without overwrite
WaitForCase(4, Clk);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, Msg => "Wr0.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 128, Msg => "Wr0.1", NextWin => true,
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, ExeSize => 4000, Msg => "Wr0.2", NextWin => true,
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, Msg => "Wr1.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ProcDone(2) := '1';
-- Ringbuf with odd framesize
end procedure;
procedure dma_resp (
signal Clk : in std_logic;
signal StrIrq : in std_logic_vector;
signal Dma_Resp : inout DaqDma2DaqSm_Resp_t;
signal Dma_Resp_Vld : inout std_logic;
signal Dma_Resp_Rdy : in std_logic;
signal TfDone : inout std_logic;
constant Generics_c : Generics_t) is
begin
-- Linear write with Overwrite
WaitForCase(0, Clk);
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
--> Finished by trigger
ApplyDmaRespAuto( Stream => 2, Trigger => '1',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
--> Next window on trigger
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ProcDone(1) := '1';
-- Ringbuf with overwrite
WaitForCase(1, Clk);
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
--> Finished by trigger
ApplyDmaRespAuto( Stream => 2, Trigger => '1',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
--> Next window on trigger
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ProcDone(1) := '1';
-- Linear without overwrite, no trigger
WaitForCase(2, Clk);
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ProcDone(1) := '1';
-- Linear without overwrite, trigger
WaitForCase(3, Clk);
ApplyDmaRespAuto( Stream => 2, Trigger => '1',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ProcDone(1) := '1';
-- Ringbuf without overwrite
WaitForCase(4, Clk);
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '1',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ProcDone(1) := '1';
end procedure;
procedure ctx (
signal Clk : in std_logic;
signal CtxStr_Cmd : in ToCtxStr_t;
signal CtxStr_Resp : inout FromCtx_t;
signal CtxWin_Cmd : in ToCtxWin_t;
signal CtxWin_Resp : inout FromCtx_t;
constant Generics_c : Generics_t) is
begin
-- Linear write with Overwrite
WaitForCase(0, Clk);
ExpCtxFullBurstAuto( Stream => 2 ,Msg => "Wr0.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, NextWin => true, Msg => "Wr0.1",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, Msg => "Wr1.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, NextWin => true, Msg => "Wr1.1",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, NextWin => true, IsTrig => true, Msg => "Wr2.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, Msg => "Wr3.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ProcDone(0) := '1';
-- Ringbuf with overwrite
WaitForCase(1, Clk);
ExpCtxFullBurstAuto( Stream => 2 ,Msg => "Wr0.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, NextWin => true, Msg => "Wr0.1",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, Msg => "Wr1.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, NextWin => true, Msg => "Wr1.1",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, NextWin => true, IsTrig => true, Msg => "Wr2.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, Msg => "Wr3.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ProcDone(0) := '1';
-- Linear without overwrite, no trigger
WaitForCase(2, Clk);
ExpCtxFullBurstAuto( Stream => 2 ,Msg => "Wr0.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, NextWin => true, Msg => "Wr0.1",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxReadAuto( Stream => 2, Msg => "SW not ready 0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxReadAuto( Stream => 2, Msg => "SW not ready 1",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
SplsWinStr_v(2)(0) := 0;
ExpCtxFullBurstAuto( Stream => 2 ,Msg => "SW ready",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ProcDone(0) := '1';
-- Linear without overwrite, trigger
WaitForCase(3, Clk);
ExpCtxFullBurstAuto( Stream => 2, NextWin => true, IsTrig => true, Msg => "Wr0.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxReadAuto( Stream => 2, Msg => "SW not ready 0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxReadAuto( Stream => 2, Msg => "SW not ready 1",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
SplsWinStr_v(2)(0) := 0;
ExpCtxFullBurstAuto( Stream => 2 ,Msg => "SW ready",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ProcDone(0) := '1';
-- Ringbuf without overwrite
WaitForCase(4, Clk);
ExpCtxFullBurstAuto( Stream => 2 ,Msg => "Wr0.0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, Msg => "Wr0.1",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, Msg => "Wr0.3", NextWin => true, IsTrig => true,
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxReadAuto( Stream => 2, Msg => "SW not ready 0",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxReadAuto( Stream => 2, Msg => "SW not ready 1",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
SplsWinStr_v(2)(0) := 0;
ExpCtxFullBurstAuto( Stream => 2 ,Msg => "SW ready",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ProcDone(0) := '1';
-- Ringbuf with odd framesize
end procedure;
end;

View File

@@ -1,230 +0,0 @@
------------------------------------------------------------
-- Libraries
------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_common_logic_pkg.all;
use work.psi_common_array_pkg.all;
use work.psi_ms_daq_pkg.all;
library work;
use work.psi_ms_daq_daq_sm_tb_pkg.all;
library work;
use work.psi_tb_txt_util.all;
use work.psi_tb_compare_pkg.all;
use work.psi_tb_activity_pkg.all;
------------------------------------------------------------
-- Package Header
------------------------------------------------------------
package psi_ms_daq_daq_sm_tb_case_timestamp is
procedure control (
signal Clk : in std_logic;
signal Rst : inout std_logic;
signal GlbEna : inout std_logic;
signal StrEna : inout std_logic_vector;
signal StrIrq : in std_logic_vector;
signal Inp_HasLast : inout std_logic_vector;
signal Inp_Level : inout t_aslv16;
signal Ts_Vld : inout std_logic_vector;
signal Ts_Rdy : in std_logic_vector;
signal Ts_Data : inout t_aslv64;
signal Dma_Cmd : in DaqSm2DaqDma_Cmd_t;
signal Dma_Cmd_Vld : in std_logic;
constant Generics_c : Generics_t);
procedure dma_cmd (
signal Clk : in std_logic;
signal StrIrq : in std_logic_vector;
signal Dma_Cmd : in DaqSm2DaqDma_Cmd_t;
signal Dma_Cmd_Vld : in std_logic;
constant Generics_c : Generics_t);
procedure dma_resp (
signal Clk : in std_logic;
signal StrIrq : in std_logic_vector;
signal Dma_Resp : inout DaqDma2DaqSm_Resp_t;
signal Dma_Resp_Vld : inout std_logic;
signal Dma_Resp_Rdy : in std_logic;
signal TfDone : inout std_logic;
constant Generics_c : Generics_t);
procedure ctx (
signal Clk : in std_logic;
signal CtxStr_Cmd : in ToCtxStr_t;
signal CtxStr_Resp : inout FromCtx_t;
signal CtxWin_Cmd : in ToCtxWin_t;
signal CtxWin_Resp : inout FromCtx_t;
constant Generics_c : Generics_t);
end package;
------------------------------------------------------------
-- Package Body
------------------------------------------------------------
package body psi_ms_daq_daq_sm_tb_case_timestamp is
procedure control (
signal Clk : in std_logic;
signal Rst : inout std_logic;
signal GlbEna : inout std_logic;
signal StrEna : inout std_logic_vector;
signal StrIrq : in std_logic_vector;
signal Inp_HasLast : inout std_logic_vector;
signal Inp_Level : inout t_aslv16;
signal Ts_Vld : inout std_logic_vector;
signal Ts_Rdy : in std_logic_vector;
signal Ts_Data : inout t_aslv64;
signal Dma_Cmd : in DaqSm2DaqDma_Cmd_t;
signal Dma_Cmd_Vld : in std_logic;
constant Generics_c : Generics_t) is
begin
print(">> -- timestamp --");
-- Timestamp handling
print(">> Timestamp handling");
InitTestCase(Clk, Rst);
TestCase := 0;
ConfigureAuto( WinSize => 4096*2, Ringbuf => '0', Overwrite => '1', Wincnt => 2, Wincur => 0);
Inp_Level(2) <= LvlThreshold_c;
for i in 0 to 4 loop
Ts_Data <= (0 to 3 => (others => '0'));
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
if i = 2 or i = 4 then
Ts_Vld(2) <= '1';
Ts_Data(2) <= std_logic_vector(to_unsigned(i*256, 64));
wait until rising_edge(Clk) and Ts_Rdy(2) = '1';
CheckLastActivity(Ts_Rdy(0), 10 us, 0);
CheckLastActivity(Ts_Rdy(1), 10 us, 0);
CheckLastActivity(Ts_Rdy(3), 10 us, 0);
Ts_Data(2) <= (others => '0');
end if;
end loop;
Ts_Vld(2) <= '0';
Inp_Level(2) <= (others => '0');
ControlWaitCompl(Clk);
-- timestamp on different stream has no effect
print(">> timestamp on different stream has no effect");
InitTestCase(Clk, Rst);
TestCase := 1;
ConfigureAuto( WinSize => 4096*2, Ringbuf => '0', Overwrite => '1', Wincnt => 2, Wincur => 0);
Inp_Level(2) <= LvlThreshold_c;
wait until rising_edge(Clk) and Dma_Cmd_Vld = '1';
Ts_Vld(0) <= '1';
Ts_Data(2) <= std_logic_vector(to_unsigned(256, 64));
Ts_Data(0) <= std_logic_vector(to_unsigned(256, 64));
wait for 1 us;
Ts_Data(2) <= std_logic_vector(to_unsigned(0, 64));
Ts_Data(0) <= std_logic_vector(to_unsigned(0, 64));
Ts_Vld(0) <= '0';
Inp_Level(2) <= (others => '0');
ControlWaitCompl(Clk);
end procedure;
procedure dma_cmd (
signal Clk : in std_logic;
signal StrIrq : in std_logic_vector;
signal Dma_Cmd : in DaqSm2DaqDma_Cmd_t;
signal Dma_Cmd_Vld : in std_logic;
constant Generics_c : Generics_t) is
begin
-- Timestamp handling
WaitForCase(0, Clk);
-- First window without trigger
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, Msg => "Wr0.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, Msg => "Wr0.1", NextWin => true,
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
-- second window trigger in first access
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, ExeSize=> 512, Msg => "Wr1.0", NextWin => true,
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
-- third window trigger in second access
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, Msg => "Wr2.0",
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, ExeSize=> 512, Msg => "Wr2.1", NextWin => true,
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ProcDone(2) := '1';
-- timestamp on different stream has no effect
WaitForCase(1, Clk);
ExpectDmaCmdAuto( Stream => 2, MaxSize => 4096, ExeSize=> 512, NextWin => true,
Clk => Clk, Dma_Cmd => Dma_Cmd, Dma_Vld => Dma_Cmd_Vld);
ProcDone(2) := '1';
end procedure;
procedure dma_resp (
signal Clk : in std_logic;
signal StrIrq : in std_logic_vector;
signal Dma_Resp : inout DaqDma2DaqSm_Resp_t;
signal Dma_Resp_Vld : inout std_logic;
signal Dma_Resp_Rdy : in std_logic;
signal TfDone : inout std_logic;
constant Generics_c : Generics_t) is
begin
-- Timestamp handling
WaitForCase(0, Clk);
-- First window without trigger
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
-- second window trigger in first access
ApplyDmaRespAuto( Stream => 2, Trigger => '1',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
-- third window trigger in second access
ApplyDmaRespAuto( Stream => 2, Trigger => '0',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ApplyDmaRespAuto( Stream => 2, Trigger => '1',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ProcDone(1) := '1';
-- timestamp on different stream has no effect
WaitForCase(1, Clk);
ApplyDmaRespAuto( Stream => 2, Trigger => '1',
Clk => Clk, Dma_Resp => Dma_Resp, Dma_Resp_Vld => Dma_Resp_Vld, Dma_Resp_Rdy => Dma_Resp_Rdy);
ProcDone(1) := '1';
end procedure;
procedure ctx (
signal Clk : in std_logic;
signal CtxStr_Cmd : in ToCtxStr_t;
signal CtxStr_Resp : inout FromCtx_t;
signal CtxWin_Cmd : in ToCtxWin_t;
signal CtxWin_Resp : inout FromCtx_t;
constant Generics_c : Generics_t) is
begin
-- Timestamp handling
WaitForCase(0, Clk);
-- First window without trigger
ExpCtxFullBurstAuto( Stream => 2, Msg => "Wr0.0", WriteTs => CheckNotWritten,
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, Msg => "Wr0.1", NextWin => true, WriteTs => CheckWritten, Timstamp => X"FFFFFFFFFFFFFFFF", -- without trigger, no timestamp is sampled
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
-- second window trigger in first access
ExpCtxFullBurstAuto( Stream => 2, Msg => "Wr1.0", NextWin => true, IsTrig => true, WriteTs => CheckWritten, Timstamp => X"0000000000000200",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
-- third window trigger in second access
ExpCtxFullBurstAuto( Stream => 2, Msg => "Wr2.0", WriteTs => CheckNotWritten,
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ExpCtxFullBurstAuto( Stream => 2, Msg => "Wr2.1", NextWin => true, IsTrig => true, WriteTs => CheckWritten, Timstamp => X"0000000000000400",
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ProcDone(0) := '1';
-- timestamp on different stream has no effect
WaitForCase(1, Clk);
ExpCtxFullBurstAuto( Stream => 2, Msg => "Wr0.1", NextWin => true, IsTrig => true, WriteTs => CheckWritten, Timstamp => X"FFFFFFFFFFFFFFFF", -- No Timestamp available
Clk => Clk, CtxStr_Cmd => CtxStr_Cmd, CtxStr_Resp => CtxStr_Resp, CtxWin_Cmd => CtxWin_Cmd, CtxWin_Resp => CtxWin_Resp);
ProcDone(0) := '1';
end procedure;
end;

View File

@@ -1,864 +0,0 @@
------------------------------------------------------------
-- Libraries
------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_common_array_pkg.all;
use work.psi_ms_daq_pkg.all;
library work;
use work.psi_tb_txt_util.all;
use work.psi_tb_compare_pkg.all;
------------------------------------------------------------
-- Package Header
------------------------------------------------------------
package psi_ms_daq_daq_sm_tb_pkg is
-- *** Generics Record ***
type Generics_t is record
Dummy : boolean; -- required since empty records are not allowed
end record;
------------------------------------------------------------
-- Not exported Generics
------------------------------------------------------------
constant MaxBurstSize_g : positive := 512;
constant StreamPrio_g : t_ainteger := (1, 2, 3, 1);
constant StreamWidth_g : t_ainteger := (8, 16, 32, 64);
constant MinBurstSize_g : positive := 512;
constant Windows_g : positive := 8;
constant Streams_g : positive := 4;
------------------------------------------------------------
-- Handwritten constants and variables
------------------------------------------------------------
constant Size4k_c : positive := 4096;
constant DataWidth_c : positive := 64;
constant DataWidthBytes_c : positive := DataWidth_c/8;
constant LvlThreshold_c : std_logic_vector(15 downto 0) := std_logic_vector(to_unsigned(Size4k_c/DataWidthBytes_c, 16));
shared variable TestCase : integer := -1;
shared variable ProcDone : std_logic_vector(0 to 2) := "000";
constant AllDone : std_logic_vector(ProcDone'range) := (others => '1');
------------------------------------------------------------
-- Test Case Control
------------------------------------------------------------
procedure InitTestCase( signal Clk : in std_logic;
signal Rst : out std_logic);
procedure FinishTestCase;
procedure ControlWaitCompl( signal Clk : in std_logic);
procedure WaitForCase( SubCase : in integer;
signal Clk : in std_logic);
------------------------------------------------------------
-- Low Level Test Functions
------------------------------------------------------------
shared variable DmaCmdOpen : integer := 0;
type CheckTs_t is (CheckWritten, CheckNotWritten, DontCheck);
procedure ExpCtxRead( Stream : in integer;
BufStart : in integer := 16#01230000#;
WinSize : in integer := 16#00100000#;
Ptr : in integer := 16#01238000#;
Ringbuf : in std_logic := '0';
Overwrite : in std_logic := '0';
Wincnt : in integer := 2;
Wincur : in integer := 0;
WinSel : in integer := -1;
SamplesWin : in integer;
WinIsTrig : in boolean := false;
signal Clk : in std_logic;
signal CtxStr_Cmd : in ToCtxStr_t;
signal CtxStr_Resp : out FromCtx_t;
signal CtxWin_Cmd : in ToCtxWin_t;
signal CtxWin_Resp : out FromCtx_t;
Msg : in string := "");
procedure ExpCtxWrite( Stream : in integer;
BufStart : in integer := 16#01230000#;
WinSize : in integer := 16#00100000#;
Ptr : in integer := 16#01238000#;
Ringbuf : in std_logic := '0';
Overwrite : in std_logic := '0';
Wincnt : in integer := 2;
Wincur : in integer := 0;
WinNext : in integer := -1;
SamplesWin : in integer;
WinIsTrig : in boolean := false;
WinLast : in integer;
WriteTs : in CheckTs_t := DontCheck;
Timstamp : in std_logic_vector(63 downto 0) := (others => 'X');
signal Clk : in std_logic;
signal CtxStr_Cmd : in ToCtxStr_t;
signal CtxWin_Cmd : in ToCtxWin_t;
Msg : in string := "");
procedure ExpCtxUpdate( Stream : in integer;
TfSize : in integer; -- in bytes
NextWin : in boolean := false;
IsTrig : in boolean := false;
BufStart : in integer := 16#01230000#;
WinSize : in integer := 16#00100000#;
PtrBefore : in integer := 16#01238000#;
Ringbuf : in std_logic := '0';
Overwrite : in std_logic := '0';
Wincnt : in integer := 2;
Wincur : in integer := 0;
SamplesWinBefore : in integer;
WriteTs : in CheckTs_t := DontCheck;
Timstamp : in std_logic_vector(63 downto 0) := (others => 'X');
variable PtrAfter : out integer;
signal Clk : in std_logic;
signal CtxStr_Cmd : in ToCtxStr_t;
signal CtxStr_Resp : out FromCtx_t;
signal CtxWin_Cmd : in ToCtxWin_t;
signal CtxWin_Resp : out FromCtx_t;
Msg : in string := "");
procedure ExpCtxFullBurst( Stream : in integer;
TfSize : in integer; -- in bytes
NextWin : in boolean := false;
BufStart : in integer := 16#01230000#;
WinSize : in integer := 16#00100000#;
PtrBefore : in integer := 16#01238000#;
Ringbuf : in std_logic := '0';
Overwrite : in std_logic := '0';
Wincnt : in integer := 2;
Wincur : in integer := 0;
SamplesWinBefore : in integer;
WriteTs : in CheckTs_t := DontCheck;
Timstamp : in std_logic_vector(63 downto 0) := (others => 'X');
variable PtrAfter : out integer;
signal Clk : in std_logic;
signal CtxStr_Cmd : in ToCtxStr_t;
signal CtxStr_Resp : out FromCtx_t;
signal CtxWin_Cmd : in ToCtxWin_t;
signal CtxWin_Resp : out FromCtx_t;
Msg : in string := "");
procedure ExpectDmaCmd( Stream : in integer;
Address : in integer;
MaxSize : in integer;
signal Clk : in std_logic;
signal Dma_Cmd : in DaqSm2DaqDma_Cmd_t;
signal Dma_Vld : in std_logic;
Msg : in string := "");
-- The DMA response is splilt into "Apply" and "Remove" because the context memory is read in between
procedure ApplyDmaResp( Stream : in integer;
Size : in integer;
Trigger : in std_logic;
Delay : in time := 0 ns;
signal Clk : in std_logic;
signal Dma_Resp : out DaqDma2DaqSm_Resp_t;
signal Dma_Resp_Vld : out std_logic;
signal Dma_Resp_Rdy : in std_logic;
Msg : in string := "");
procedure AssertTfDone( signal Clk : in std_logic;
signal TfDone : out std_logic);
procedure CheckIrq( MaxWait : in time := 1 us; -- Maximum time to wait for the IRQ
Stream : in integer;
Msg : in string := "";
signal Clk : in std_logic;
signal StrIrq : in std_logic_vector(3 downto 0));
------------------------------------------------------------
-- High Level (Auto) Functions
------------------------------------------------------------
type IntStrWin_t is array (0 to 3) of t_ainteger(0 to 31);
shared variable PtrStr_v : t_ainteger(0 to 3);
shared variable PtrDma_v : t_ainteger(0 to 3);
shared variable SplsWinStr_v : IntStrWin_t;
constant BufStart_c : t_ainteger(0 to 3) := (16#01230000#, 16#02230000#, 16#03230000#, 16#04230000#);
shared variable AutoWinSize_v : integer;
shared variable AutoRingbuf_v : std_logic;
shared variable AutoOverwrite_v : std_logic;
shared variable AutoWincnt_v : integer;
shared variable AutoWincur_v : t_ainteger(0 to 3);
shared variable AutoAccessSize_v : t_ainteger(0 to 3);
procedure ExpCtxReadAuto( Stream : in integer;
signal Clk : in std_logic;
signal CtxStr_Cmd : in ToCtxStr_t;
signal CtxStr_Resp : out FromCtx_t;
signal CtxWin_Cmd : in ToCtxWin_t;
signal CtxWin_Resp : out FromCtx_t;
Msg : in string := "");
procedure ExpCtxUpdateAuto( Stream : in integer;
NextWin : in boolean := false;
IsTrig : in boolean := false;
WriteTs : in CheckTs_t := DontCheck;
Timstamp : in std_logic_vector(63 downto 0) := (others => 'X');
signal Clk : in std_logic;
signal CtxStr_Cmd : in ToCtxStr_t;
signal CtxStr_Resp : out FromCtx_t;
signal CtxWin_Cmd : in ToCtxWin_t;
signal CtxWin_Resp : out FromCtx_t;
Msg : in string := "");
procedure ExpCtxFullBurstAuto( Stream : in integer;
NextWin : in boolean := false;
IsTrig : in boolean := false;
WriteTs : in CheckTs_t := DontCheck;
Timstamp : in std_logic_vector(63 downto 0) := (others => 'X');
signal Clk : in std_logic;
signal CtxStr_Cmd : in ToCtxStr_t;
signal CtxStr_Resp : out FromCtx_t;
signal CtxWin_Cmd : in ToCtxWin_t;
signal CtxWin_Resp : out FromCtx_t;
Msg : in string := "");
procedure ConfigureAuto( WinSize : in integer := 16#00100000#;
Ringbuf : in std_logic := '0';
Overwrite : in std_logic := '0';
Wincnt : in integer := 2;
Wincur : in integer := 0);
procedure ExpectDmaCmdAuto( Stream : in integer;
MaxSize : in integer;
ExeSize : in integer := -1;
NextWin : in boolean := false;
signal Clk : in std_logic;
signal Dma_Cmd : in DaqSm2DaqDma_Cmd_t;
signal Dma_Vld : in std_logic;
Msg : in string := "");
procedure ApplyDmaRespAuto( Stream : in integer;
Trigger : in std_logic;
Delay : in time := 0 ns;
signal Clk : in std_logic;
signal Dma_Resp : out DaqDma2DaqSm_Resp_t;
signal Dma_Resp_Vld : out std_logic;
signal Dma_Resp_Rdy : in std_logic;
Msg : in string := "");
------------------------------------------------------------
-- Helper Functions
------------------------------------------------------------
function GetWindowOffset( Stream : integer;
Ptr : integer;
AutoWincur_v : t_ainteger;
AutoWinSize_v : integer) return integer;
end package;
------------------------------------------------------------
-- Package Body
------------------------------------------------------------
package body psi_ms_daq_daq_sm_tb_pkg is
procedure InitTestCase( signal Clk : in std_logic;
signal Rst : out std_logic) is
begin
ConfigureAuto;
ProcDone := (others => '0');
TestCase := -1;
DmaCmdOpen := 0;
PtrStr_v := BufStart_c;
PtrDma_v := BufStart_c;
SplsWinStr_v := (others => (others => 0));
wait until rising_edge(Clk);
Rst <= '1';
wait until rising_edge(Clk);
wait until rising_edge(Clk);
Rst <= '0';
wait until rising_edge(Clk);
end procedure;
procedure FinishTestCase is
begin
TestCase := -1;
wait for 1 us;
end procedure;
procedure ControlWaitCompl( signal Clk : in std_logic) is
begin
while ProcDone /= AllDone loop
wait until rising_edge(Clk);
end loop;
ProcDone := (others => '0');
end procedure;
procedure WaitForCase( SubCase : in integer;
signal Clk : in std_logic) is
begin
while TestCase /= SubCase loop
wait until rising_edge(Clk);
end loop;
end procedure;
procedure ExpCtxRead( Stream : in integer;
BufStart : in integer := 16#01230000#;
WinSize : in integer := 16#00100000#;
Ptr : in integer := 16#01238000#;
Ringbuf : in std_logic := '0';
Overwrite : in std_logic := '0';
Wincnt : in integer := 2;
Wincur : in integer := 0;
WinSel : in integer := -1;
SamplesWin : in integer;
WinIsTrig : in boolean := false;
signal Clk : in std_logic;
signal CtxStr_Cmd : in ToCtxStr_t;
signal CtxStr_Resp : out FromCtx_t;
signal CtxWin_Cmd : in ToCtxWin_t;
signal CtxWin_Resp : out FromCtx_t;
Msg : in string := "") is
variable WindowSel_v : integer;
begin
if WinSel = -1 then
WindowSel_v := Wincur;
else
WindowSel_v := WinSel;
end if;
for acc in 0 to 3 loop -- 3 read accesses are expected for stream context, 1 for window context
wait until rising_edge(Clk) and ((CtxStr_Cmd.Rd = '1') or (CtxWin_Cmd.Rd = '1'));
CtxStr_Resp.RdatLo <= (others => '0');
CtxStr_Resp.RdatHi <= (others => '0');
if CtxStr_Cmd.Rd = '1' then
IntCompare(Stream, CtxStr_Cmd.Stream, "ApplyContext.Str: Wrong stream number - " & Msg);
StdlCompare(0, CtxStr_Cmd.WenLo, "ApplyContext.Str: WenLo asserted - " & Msg);
StdlCompare(0, CtxStr_Cmd.WenHi, "ApplyContext.Str: WenHi asserted - " & Msg);
case CtxStr_Cmd.Sel is
when CtxStr_Sel_ScfgBufstart_c => CtxStr_Resp.RdatLo(CtxStr_Sft_SCFG_RINGBUF_c) <= Ringbuf;
CtxStr_Resp.RdatLo(CtxStr_Sft_SCFG_OVERWRITE_c) <= Overwrite;
CtxStr_Resp.RdatLo(CtxStr_Sft_SCFG_WINCNT_c+7 downto CtxStr_Sft_SCFG_WINCNT_c) <= std_logic_vector(to_unsigned(Wincnt, 8));
CtxStr_Resp.RdatLo(CtxStr_Sft_SCFG_WINCUR_c+7 downto CtxStr_Sft_SCFG_WINCUR_c) <= std_logic_vector(to_unsigned(Wincur, 8));
CtxStr_Resp.RdatHi <= std_logic_vector(to_unsigned(BufStart, 32));
when CtxStr_Sel_WinsizePtr_c => CtxStr_Resp.RdatLo <= std_logic_vector(to_unsigned(WinSize, 32));
CtxStr_Resp.RdatHi <= std_logic_vector(to_unsigned(Ptr, 32));
when CtxStr_Sel_Winend_c => CtxStr_Resp.RdatLo <= std_logic_vector(to_unsigned(BufStart+WinSize*(Wincur+1), 32));
when others => report "###ERROR###: ApplyContext.Str: illegal CtxStr_Cmd.Sel - " & Msg severity error;
end case;
elsif CtxWin_Cmd.Rd = '1' then
IntCompare(Stream, CtxWin_Cmd.Stream, "ApplyContext.Win: Wrong stream number - " & Msg);
IntCompare(WindowSel_v, CtxWin_Cmd.Window, "ApplyContext.Win: Wrong window number - " & Msg);
StdlCompare(0, CtxWin_Cmd.WenLo, "ApplyContext.Win: WenLo asserted - " & Msg);
StdlCompare(0, CtxWin_Cmd.WenHi, "ApplyContext.Win: WenHi asserted - " & Msg);
case CtxWin_Cmd.Sel is
when CtxWin_Sel_WincntWinlast_c => CtxWin_Resp.RdatLo(30 downto 0) <= std_logic_vector(to_unsigned(SamplesWin, 31));
if WinIsTrig then
CtxWin_Resp.RdatLo(31) <= '1';
else
CtxWin_Resp.RdatLo(31) <= '0';
end if;
when others => report "###ERROR###: ApplyContext.Win: illegal CtxStr_Cmd.Sel - " & Msg severity error;
end case;
end if;
end loop;
end procedure;
procedure ExpCtxWrite( Stream : in integer;
BufStart : in integer := 16#01230000#;
WinSize : in integer := 16#00100000#;
Ptr : in integer := 16#01238000#;
Ringbuf : in std_logic := '0';
Overwrite : in std_logic := '0';
Wincnt : in integer := 2;
Wincur : in integer := 0;
WinNext : in integer := -1;
SamplesWin : in integer;
WinIsTrig : in boolean := false;
WinLast : in integer;
WriteTs : in CheckTs_t := DontCheck;
Timstamp : in std_logic_vector(63 downto 0) := (others => 'X');
signal Clk : in std_logic;
signal CtxStr_Cmd : in ToCtxStr_t;
signal CtxWin_Cmd : in ToCtxWin_t;
Msg : in string := "") is
variable WinNext_v : integer;
begin
-- No window change by default
if WinNext = -1 then
WinNext_v := Wincur;
else
WinNext_v := WinNext;
end if;
wait until rising_edge(Clk) and CtxStr_Cmd.WenLo = '1';
-- Stream
IntCompare(Stream, CtxStr_Cmd.Stream, "ExpectContext.Str: Wrong stream number 0 - " & Msg);
StdlvCompareStdlv(CtxStr_Sel_ScfgBufstart_c, CtxStr_Cmd.Sel, "ExpectContext.Str: Wrong Sel (unexpected sequence 0) - " & Msg);
StdlCompare(0, CtxStr_Cmd.WenHi, "ExpectContext.Str: WenHi asserted in first cycle (BufStart overwritten) - " & Msg);
StdlCompare(choose(Ringbuf='1',1,0), CtxStr_Cmd.WdatLo(CtxStr_Sft_SCFG_RINGBUF_c), "ExpectContext.Str: Wrong RINGBUFFER - " & Msg);
StdlCompare(choose(Overwrite='1',1,0), CtxStr_Cmd.WdatLo(CtxStr_Sft_SCFG_OVERWRITE_c), "ExpectContext.Str: Wrong OVERWRITE - " & Msg);
StdlvCompareInt(Wincnt, CtxStr_Cmd.WdatLo(CtxStr_Sft_SCFG_WINCNT_c+7 downto CtxStr_Sft_SCFG_WINCNT_c), "ExpectContext.Str: Wrong SCFG_WINCNT - " & Msg);
StdlvCompareInt(WinNext_v, CtxStr_Cmd.WdatLo(CtxStr_Sft_SCFG_WINCUR_c+7 downto CtxStr_Sft_SCFG_WINCUR_c), "ExpectContext.Str: Wrong SCFG_WINCUR - " & Msg);
-- Window
IntCompare(Stream, CtxWin_Cmd.Stream, "ExpectContext.Win: Wrong stream number 0 - " & Msg);
IntCompare(Wincur, CtxWin_Cmd.Window, "ExpectContext.Win: Wrong Window number 0 - " & Msg);
StdlCompare(1, CtxWin_Cmd.WenLo, "ExpectContext.Win: WenLo not asserted in first cycle - " & Msg);
StdlCompare(1, CtxWin_Cmd.WenHi, "ExpectContext.Win: WenHi not asserted in first cycle - " & Msg);
StdlvCompareInt(SamplesWin, CtxWin_Cmd.WdatLo(30 downto 0), "ExpectContext.Win: Wrong WIN_WINCNT - " & Msg);
StdlCompare(Choose(WinIsTrig, 1, 0), CtxWin_Cmd.WdatLo(31), "ExpectContext.Win Wrong WIN_ISTRIG - " & Msg);
StdlvCompareInt(WinLast, CtxWin_Cmd.WdatHi, "ExpectContext.Str: Wrong WIN_WINLAST - " & Msg);
wait until rising_edge(Clk) and CtxStr_Cmd.WenHi = '1';
-- Stream
IntCompare(Stream, CtxStr_Cmd.Stream, "ExpectContext.Str: Wrong stream number 1 - " & Msg);
StdlvCompareStdlv(CtxStr_Sel_WinsizePtr_c, CtxStr_Cmd.Sel, "ExpectContext.Str: Wrong Sel (unexpected sequence 1) - " & Msg);
StdlCompare(0, CtxStr_Cmd.WenLo, "ExpectContext.Str: WenLo asserted in second cycle (WinSize overwritten) - " & Msg);
StdlvCompareInt(Ptr, CtxStr_Cmd.WdatHi, "ExpectContext.Str: Wrong PTR - " & Msg);
-- Window
if WriteTs = CheckWritten then
IntCompare(Stream, CtxWin_Cmd.Stream, "ExpectContext.Win: Wrong stream number 1 - " & Msg);
IntCompare(Wincur, CtxWin_Cmd.Window, "ExpectContext.Win: Wrong Window number 1 - " & Msg);
StdlCompare(1, CtxWin_Cmd.WenLo, "ExpectContext.Win: WenLo not asserted in scond cycle - " & Msg);
StdlCompare(1, CtxWin_Cmd.WenHi, "ExpectContext.Win: WenHi not asserted in second cycle - " & Msg);
StdlvCompareStdlv(Timstamp(31 downto 0), CtxWin_Cmd.WdatLo, "ExpectContext.Str: Wrong TS-LO - " & Msg);
StdlvCompareStdlv(Timstamp(63 downto 32), CtxWin_Cmd.WdatHi, "ExpectContext.Str: Wrong TS-HI - " & Msg);
elsif WriteTs = CheckNotWritten then
StdlCompare(0, CtxWin_Cmd.WenLo, "ExpectContext.Win: WenLo asserted in scond cycle (without TS) - " & Msg);
StdlCompare(0, CtxWin_Cmd.WenHi, "ExpectContext.Win: WenHi asserted in scond cycle (without TS) - " & Msg);
end if;
wait until rising_edge(Clk) and CtxStr_Cmd.WenLo = '1';
-- Stream
IntCompare(Stream, CtxStr_Cmd.Stream, "ExpectContext.Str: Wrong stream number 2 - " & Msg);
StdlvCompareStdlv(CtxStr_Sel_Winend_c, CtxStr_Cmd.Sel, "ExpectContext.Str: Wrong Sel (unexpected sequence 2) - " & Msg);
StdlCompare(0, CtxStr_Cmd.WenHi, "ExpectContext.Str: WenHi asserted in third cycle (Unused overwritten) - " & Msg);
StdlvCompareInt(BufStart+WinSize*(WinNext_v+1), CtxStr_Cmd.WdatLo, "ExpectContext.Str: Wrong WINEND - " & Msg);
end procedure;
procedure ExpCtxUpdate( Stream : in integer;
TfSize : in integer; -- in bytes
NextWin : in boolean := false;
IsTrig : in boolean := false;
BufStart : in integer := 16#01230000#;
WinSize : in integer := 16#00100000#;
PtrBefore : in integer := 16#01238000#;
Ringbuf : in std_logic := '0';
Overwrite : in std_logic := '0';
Wincnt : in integer := 2;
Wincur : in integer := 0;
SamplesWinBefore : in integer;
WriteTs : in CheckTs_t := DontCheck;
Timstamp : in std_logic_vector(63 downto 0) := (others => 'X');
variable PtrAfter : out integer;
signal Clk : in std_logic;
signal CtxStr_Cmd : in ToCtxStr_t;
signal CtxStr_Resp : out FromCtx_t;
signal CtxWin_Cmd : in ToCtxWin_t;
signal CtxWin_Resp : out FromCtx_t;
Msg : in string := "") is
variable PtrAfter_v : integer;
variable SampleswinAfter_v : integer;
variable WinLastAfter_v : integer;
constant StrWidthBytes_c : integer := StreamWidth_g(Stream)/8;
variable WinAfter_v : integer;
begin
-- Calculations
PtrAfter_v := PtrBefore + TfSize;
SampleswinAfter_v := SamplesWinBefore + TfSize/StrWidthBytes_c;
if SampleswinAfter_v > WinSize/StrWidthBytes_c then
SampleswinAfter_v := WinSize/StrWidthBytes_c;
end if;
WinLastAfter_v := PtrBefore + TfSize - StrWidthBytes_c;
if NextWin then
if Wincur = Wincnt then
WinAfter_v := 0;
else
WinAfter_v := Wincur + 1;
end if;
PtrAfter_v := BufStart+WinAfter_v*WinSize;
else
WinAfter_v := Wincur;
-- wraparound for ringbuffer
if Ringbuf = '1' then
if PtrAfter_v >= BufStart + (Wincur+1)*WinSize then
PtrAfter_v := PtrAfter_v - WinSize;
end if;
end if;
end if;
-- Read
ExpCtxRead( Stream => Stream,
BufStart => BufStart,
WinSize => WinSize,
Ptr => PtrBefore,
Ringbuf => Ringbuf,
Overwrite => Overwrite,
Wincnt => Wincnt,
Wincur => Wincur,
SamplesWin => SamplesWinBefore,
Clk => Clk,
CtxStr_Cmd => CtxStr_Cmd,
CtxStr_Resp => CtxStr_Resp,
CtxWin_Cmd => CtxWin_Cmd,
CtxWin_Resp => CtxWin_Resp,
Msg => Msg);
-- Write
ExpCtxWrite(Stream => Stream,
BufStart => BufStart,
WinSize => WinSize,
Ptr => PtrAfter_v,
Ringbuf => Ringbuf,
Overwrite => Overwrite,
Wincnt => Wincnt,
Wincur => Wincur,
WinNext => WinAfter_v,
SamplesWin => SampleswinAfter_v,
WinIsTrig => IsTrig,
WinLast => WinLastAfter_v,
WriteTs => WriteTs,
Timstamp => Timstamp,
Clk => Clk,
CtxStr_Cmd => CtxStr_Cmd,
CtxWin_Cmd => CtxWin_Cmd,
Msg => Msg);
-- Output Values
PtrAfter := PtrAfter_v;
end procedure;
procedure ExpCtxFullBurst( Stream : in integer;
TfSize : in integer; -- in bytes
NextWin : in boolean := false;
BufStart : in integer := 16#01230000#;
WinSize : in integer := 16#00100000#;
PtrBefore : in integer := 16#01238000#;
Ringbuf : in std_logic := '0';
Overwrite : in std_logic := '0';
Wincnt : in integer := 2;
Wincur : in integer := 0;
SamplesWinBefore : in integer;
WriteTs : in CheckTs_t := DontCheck;
Timstamp : in std_logic_vector(63 downto 0) := (others => 'X');
variable PtrAfter : out integer;
signal Clk : in std_logic;
signal CtxStr_Cmd : in ToCtxStr_t;
signal CtxStr_Resp : out FromCtx_t;
signal CtxWin_Cmd : in ToCtxWin_t;
signal CtxWin_Resp : out FromCtx_t;
Msg : in string := "") is
begin
-- context read
ExpCtxRead( Stream => Stream,
BufStart => BufStart,
WinSize => WinSize,
Ptr => PtrBefore,
Ringbuf => Ringbuf,
Overwrite => Overwrite,
Wincnt => Wincnt,
Wincur => Wincur,
SamplesWin => SamplesWinBefore,
Clk => Clk,
CtxStr_Cmd => CtxStr_Cmd,
CtxStr_Resp => CtxStr_Resp,
CtxWin_Cmd => CtxWin_Cmd,
CtxWin_Resp => CtxWin_Resp,
Msg => Msg);
-- context update
ExpCtxUpdate( Stream => Stream,
TfSize => TfSize,
NextWin => NextWin,
BufStart => BufStart,
WinSize => WinSize,
PtrBefore => PtrBefore,
Ringbuf => Ringbuf,
Overwrite => Overwrite,
Wincnt => Wincnt,
Wincur => Wincur,
SamplesWinBefore => SamplesWinBefore,
WriteTs => WriteTs,
Timstamp => Timstamp,
PtrAfter => PtrAfter,
Clk => Clk,
CtxStr_Cmd => CtxStr_Cmd,
CtxStr_Resp => CtxStr_Resp,
CtxWin_Cmd => CtxWin_Cmd,
CtxWin_Resp => CtxWin_Resp,
Msg => Msg);
end procedure;
procedure ExpectDmaCmd( Stream : in integer;
Address : in integer;
MaxSize : in integer;
signal Clk : in std_logic;
signal Dma_Cmd : in DaqSm2DaqDma_Cmd_t;
signal Dma_Vld : in std_logic;
Msg : in string := "") is
begin
wait until rising_edge(Clk) and Dma_Vld = '1';
IntCompare(Stream, Dma_Cmd.Stream, "ExpectDmaCmd: Wrong stream number - " & Msg);
StdlvCompareInt (Address, Dma_Cmd.Address, "ExpectDmaCmd: Wrong address - " & Msg);
StdlvCompareInt (MaxSize, Dma_Cmd.MaxSize, "ExpectDmaCmd: Wrong MaxSize - " & Msg);
wait until rising_edge(Clk);
StdlCompare(0, Dma_Vld, "ExpectDmaCmd: Vld asserted for more than one cycle - " & Msg);
DmaCmdOpen := DmaCmdOpen + 1;
end procedure;
procedure ApplyDmaResp( Stream : in integer;
Size : in integer;
Trigger : in std_logic;
Delay : in time := 0 ns;
signal Clk : in std_logic;
signal Dma_Resp : out DaqDma2DaqSm_Resp_t;
signal Dma_Resp_Vld : out std_logic;
signal Dma_Resp_Rdy : in std_logic;
Msg : in string := "") is
begin
while DmaCmdOpen = 0 loop
wait until rising_edge(Clk);
end loop;
wait for Delay;
-- Send response
wait until rising_edge(Clk);
Dma_Resp_Vld <= '1';
Dma_Resp.Stream <= Stream;
Dma_Resp.Size <= std_logic_vector(to_unsigned(Size, Dma_Resp.Size'length));
Dma_Resp.Trigger <= Trigger;
wait until rising_edge(Clk) and Dma_Resp_Rdy = '1';
Dma_Resp_Vld <= '0';
Dma_Resp.Stream <= 0;
Dma_Resp.Trigger <= 'U';
Dma_Resp.Size <= (others => 'U');
DmaCmdOpen := DmaCmdOpen - 1;
end procedure;
procedure AssertTfDone( signal Clk : in std_logic;
signal TfDone : out std_logic) is
begin
wait until rising_edge(Clk);
TfDone <= '1';
wait until rising_edge(Clk);
TfDone <= '0';
end procedure;
procedure CheckIrq( MaxWait : in time := 1 us; -- Maximum time to wait for the IRQ
Stream : in integer;
Msg : in string := "";
signal Clk : in std_logic;
signal StrIrq : in std_logic_vector(3 downto 0)) is
variable IrqMask_v : std_logic_vector(StrIrq'range);
variable IdleTimePrior_v : time;
variable ProcStartTime_v : time;
begin
ProcStartTime_v := now;
IrqMask_v := (others => '0');
IrqMask_v(Stream) := '1';
wait until rising_edge(Clk);
wait until (StrIrq = IrqMask_v) and rising_edge(Clk) for MaxWait;
StdlvCompareStdlv (IrqMask_v, StrIrq, "IRQ was not asserted - " & Msg);
wait until rising_edge(Clk);
StdlvCompareInt (0, StrIrq, "IRQ was not deasserted - " & Msg);
end procedure;
procedure ExpCtxReadAuto( Stream : in integer;
signal Clk : in std_logic;
signal CtxStr_Cmd : in ToCtxStr_t;
signal CtxStr_Resp : out FromCtx_t;
signal CtxWin_Cmd : in ToCtxWin_t;
signal CtxWin_Resp : out FromCtx_t;
Msg : in string := "") is
begin
ExpCtxRead( Stream => Stream,
BufStart => BufStart_c(Stream),
WinSize => AutoWinSize_v,
Ptr => PtrStr_v(Stream),
Ringbuf => AutoRingbuf_v,
Overwrite => AutoOverwrite_v,
Wincnt => AutoWincnt_v,
Wincur => AutoWincur_v(Stream),
SamplesWin => SplsWinStr_v(Stream)(AutoWincur_v(Stream)),
Clk => Clk,
CtxStr_Cmd => CtxStr_Cmd,
CtxStr_Resp => CtxStr_Resp,
CtxWin_Cmd => CtxWin_Cmd,
CtxWin_Resp => CtxWin_Resp,
Msg => Msg);
end procedure;
procedure ExpCtxUpdateAuto( Stream : in integer;
NextWin : in boolean := false;
IsTrig : in boolean := false;
WriteTs : in CheckTs_t := DontCheck;
Timstamp : in std_logic_vector(63 downto 0) := (others => 'X');
signal Clk : in std_logic;
signal CtxStr_Cmd : in ToCtxStr_t;
signal CtxStr_Resp : out FromCtx_t;
signal CtxWin_Cmd : in ToCtxWin_t;
signal CtxWin_Resp : out FromCtx_t;
Msg : in string := "") is
begin
while DmaCmdOpen = 0 loop
wait until rising_edge(Clk);
end loop;
ExpCtxUpdate( Stream => Stream,
TfSize => AutoAccessSize_v(Stream),
NextWin => NextWin,
IsTrig => IsTrig,
BufStart => BufStart_c(Stream),
WinSize => AutoWinSize_v,
PtrBefore => PtrStr_v(Stream),
Ringbuf => AutoRingbuf_v,
Overwrite => AutoOverwrite_v,
Wincnt => AutoWincnt_v,
Wincur => AutoWincur_v(Stream),
SamplesWinBefore => SplsWinStr_v(Stream)(AutoWincur_v(Stream)),
WriteTs => WriteTs,
Timstamp => Timstamp,
PtrAfter => PtrStr_v(Stream),
Clk => Clk,
CtxStr_Cmd => CtxStr_Cmd,
CtxStr_Resp => CtxStr_Resp,
CtxWin_Cmd => CtxWin_Cmd,
CtxWin_Resp => CtxWin_Resp,
Msg => Msg);
SplsWinStr_v(Stream)(AutoWincur_v(Stream)) := work.psi_common_math_pkg.min(AutoWinSize_v/(StreamWidth_g(Stream)/8), SplsWinStr_v(Stream)(AutoWincur_v(Stream))+AutoAccessSize_v(Stream)/(StreamWidth_g(Stream)/8));
if NextWin then
if AutoWincur_v(Stream) = AutoWincnt_v then
AutoWincur_v(Stream) := 0;
else
AutoWincur_v(Stream) := AutoWincur_v(Stream) + 1;
end if;
else
-- wraparound for ringbuffer case
if GetWindowOffset(Stream, PtrStr_v(Stream), AutoWincur_v, AutoWinSize_v) > AutoWinSize_v then
report "###ERROR### TB assertion, unhandled window crossing" severity error;
elsif GetWindowOffset(Stream, PtrStr_v(Stream), AutoWincur_v, AutoWinSize_v) = AutoWinSize_v then
if AutoRingbuf_v = '1' then
PtrStr_v(Stream) := BufStart_c(Stream);
end if;
end if;
end if;
end procedure;
procedure ExpCtxFullBurstAuto( Stream : in integer;
NextWin : in boolean := false;
IsTrig : in boolean := false;
WriteTs : in CheckTs_t := DontCheck;
Timstamp : in std_logic_vector(63 downto 0) := (others => 'X');
signal Clk : in std_logic;
signal CtxStr_Cmd : in ToCtxStr_t;
signal CtxStr_Resp : out FromCtx_t;
signal CtxWin_Cmd : in ToCtxWin_t;
signal CtxWin_Resp : out FromCtx_t;
Msg : in string := "") is
begin
ExpCtxReadAuto( Stream => Stream,
Clk => Clk,
CtxStr_Cmd => CtxStr_Cmd,
CtxStr_Resp => CtxStr_Resp,
CtxWin_Cmd => CtxWin_Cmd,
CtxWin_Resp => CtxWin_Resp,
Msg => Msg);
ExpCtxUpdateAuto( Stream => Stream,
NextWin => NextWin,
IsTrig => IsTrig,
WriteTs => WriteTs,
Timstamp => Timstamp,
Clk => Clk,
CtxStr_Cmd => CtxStr_Cmd,
CtxStr_Resp => CtxStr_Resp,
CtxWin_Cmd => CtxWin_Cmd,
CtxWin_Resp => CtxWin_Resp,
Msg => Msg);
end procedure;
procedure ConfigureAuto( WinSize : in integer := 16#00100000#;
Ringbuf : in std_logic := '0';
Overwrite : in std_logic := '0';
Wincnt : in integer := 2;
Wincur : in integer := 0) is
begin
AutoWinSize_v := WinSize;
AutoRingbuf_v := Ringbuf;
AutoOverwrite_v := Overwrite;
AutoWincnt_v := Wincnt;
AutoWincur_v := (others => Wincur);
end procedure;
procedure ExpectDmaCmdAuto( Stream : in integer;
MaxSize : in integer;
ExeSize : in integer := -1;
NextWin : in boolean := false;
signal Clk : in std_logic;
signal Dma_Cmd : in DaqSm2DaqDma_Cmd_t;
signal Dma_Vld : in std_logic;
Msg : in string := "") is
variable ExeSize_v : integer;
variable NextWinNr_v : integer;
begin
if ExeSize = -1 then
ExeSize_v := MaxSize;
else
ExeSize_v := ExeSize;
end if;
ExpectDmaCmd( Stream => Stream,
Address => PtrDma_v(Stream),
MaxSize => MaxSize,
Clk => Clk,
Dma_Cmd => Dma_Cmd,
Dma_Vld => Dma_Vld,
Msg => Msg);
if NextWin then
if AutoWincur_v(Stream) = AutoWincnt_v then
NextWinNr_v := 0;
else
NextWinNr_v := AutoWincur_v(Stream) + 1;
end if;
PtrDma_v(Stream) := BufStart_c(Stream) + NextWinNr_v*AutoWinSize_v;
else
PtrDma_v(Stream) := PtrDma_v(Stream) + ExeSize_v;
-- wraparound for ringbuffer case
if GetWindowOffset(Stream, PtrDma_v(Stream), AutoWincur_v, AutoWinSize_v) > AutoWinSize_v then
report "###ERROR### TB assertion, unhandled window crossing" severity error;
elsif GetWindowOffset(Stream, PtrDma_v(Stream), AutoWincur_v, AutoWinSize_v) = AutoWinSize_v then
if AutoRingbuf_v = '1' then
PtrDma_v(Stream) := BufStart_c(Stream) + AutoWincur_v(Stream)*AutoWinSize_v;
end if;
end if;
end if;
AutoAccessSize_v(Stream) := ExeSize_v;
end procedure;
procedure ApplyDmaRespAuto( Stream : in integer;
Trigger : in std_logic;
Delay : in time := 0 ns;
signal Clk : in std_logic;
signal Dma_Resp : out DaqDma2DaqSm_Resp_t;
signal Dma_Resp_Vld : out std_logic;
signal Dma_Resp_Rdy : in std_logic;
Msg : in string := "") is
begin
while DmaCmdOpen = 0 loop
wait until rising_edge(Clk);
end loop;
wait for 1 ps;
ApplyDmaResp( Stream => Stream,
Size => AutoAccessSize_v(Stream),
Trigger => Trigger,
Delay => Delay,
Clk => Clk,
Dma_Resp => Dma_Resp,
Dma_Resp_Vld => Dma_Resp_Vld,
Dma_Resp_Rdy => Dma_Resp_Rdy,
Msg => Msg);
end procedure;
function GetWindowOffset( Stream : integer;
Ptr : integer;
AutoWincur_v : t_ainteger;
AutoWinSize_v : integer) return integer is
begin
return Ptr - BufStart_c(Stream) - AutoWincur_v(Stream)*AutoWinSize_v;
end function;
end;

View File

@@ -1,328 +0,0 @@
------------------------------------------------------------
-- Testbench generated by TbGen.py
------------------------------------------------------------
-- see Library/Python/TbGenerator
------------------------------------------------------------
-- Libraries
------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_ms_daq_pkg.all;
library work;
use work.psi_tb_txt_util.all;
library work;
use work.psi_ms_daq_input_tb_pkg.all;
library work;
use work.psi_ms_daq_input_tb_case_single_frame.all;
use work.psi_ms_daq_input_tb_case_multi_frame.all;
use work.psi_ms_daq_input_tb_case_timeout.all;
use work.psi_ms_daq_input_tb_case_ts_overflow.all;
use work.psi_ms_daq_input_tb_case_trig_in_posttrig.all;
use work.psi_ms_daq_input_tb_case_always_trig.all;
use work.psi_ms_daq_input_tb_case_backpressure.all;
use work.psi_ms_daq_input_tb_case_modes.all;
------------------------------------------------------------
-- Entity Declaration
------------------------------------------------------------
entity psi_ms_daq_input_tb is
generic (
StreamWidth_g : positive := 16;
VldPulsed_g : boolean := false
);
end entity;
------------------------------------------------------------
-- Architecture
------------------------------------------------------------
architecture sim of psi_ms_daq_input_tb is
-- *** Fixed Generics ***
constant StreamBuffer_g : positive := 32;
constant StreamTimeout_g : real := 10.0e-6;
constant StreamClkFreq_g : real := 125.0e6;
constant StreamTsFifoDepth_g : positive := 8;
constant StreamUseTs_g : boolean := true;
-- *** Not Assigned Generics (default values) ***
-- *** Exported Generics ***
constant Generics_c : Generics_t := (
StreamWidth_g => StreamWidth_g,
VldPulsed_g => VldPulsed_g);
-- *** TB Control ***
signal TbRunning : boolean := True;
signal NextCase : integer := -1;
signal ProcessDone : std_logic_vector(0 to 1) := (others => '0');
constant AllProcessesDone_c : std_logic_vector(0 to 1) := (others => '1');
constant TbProcNr_stream_c : integer := 0;
constant TbProcNr_daq_c : integer := 1;
-- *** DUT Signals ***
signal Str_Clk : std_logic := '1';
signal Str_Vld : std_logic := '0';
signal Str_Rdy : std_logic := '0';
signal Str_Data : std_logic_vector(StreamWidth_g-1 downto 0) := (others => '0');
signal Str_Trig : std_logic := '0';
signal Str_Ts : std_logic_vector(63 downto 0) := (others => '0');
signal ClkTmem : std_logic := '1';
signal RstTmem : std_logic := '1';
signal ClkSmem : std_logic := '1';
signal RstSmem : std_logic := '1';
signal PostTrigSpls : std_logic_vector(31 downto 0) := (others => '0');
signal Mode : RecMode_t := (others => '0');
signal Arm : std_logic := '0';
signal IsArmed : std_logic := '0';
signal Daq_Vld : std_logic := '0';
signal Daq_Rdy : std_logic := '0';
signal Daq_Data : Input2Daq_Data_t;
signal Daq_Level : std_logic_vector(15 downto 0) := (others => '0');
signal Daq_HasLast : std_logic := '0';
signal Ts_Vld : std_logic := '0';
signal Ts_Rdy : std_logic := '0';
signal Ts_Data : std_logic_vector(63 downto 0) := (others => '0');
begin
------------------------------------------------------------
-- DUT Instantiation
------------------------------------------------------------
i_dut : entity work.psi_ms_daq_input
generic map (
StreamWidth_g => StreamWidth_g,
StreamBuffer_g => StreamBuffer_g,
StreamTimeout_g => StreamTimeout_g,
StreamClkFreq_g => StreamClkFreq_g,
StreamTsFifoDepth_g => StreamTsFifoDepth_g,
StreamUseTs_g => StreamUseTs_g
)
port map (
Str_Clk => Str_Clk,
Str_Vld => Str_Vld,
Str_Rdy => Str_Rdy,
Str_Data => Str_Data,
Str_Trig => Str_Trig,
Str_Ts => Str_Ts,
ClkTmem => ClkTmem,
RstTmem => RstTmem,
PostTrigSpls => PostTrigSpls,
Mode => Mode,
Arm => Arm,
IsArmed => IsArmed,
ClkSmem => ClkSmem,
RstSmem => RstSmem,
Daq_Vld => Daq_Vld,
Daq_Rdy => Daq_Rdy,
Daq_Data => Daq_Data,
Daq_Level => Daq_Level,
Daq_HasLast => Daq_HasLast,
Ts_Vld => Ts_Vld,
Ts_Rdy => Ts_Rdy,
Ts_Data => Ts_Data
);
------------------------------------------------------------
-- Testbench Control !DO NOT EDIT!
------------------------------------------------------------
p_tb_control : process
begin
wait until RstTmem = '0' and RstSmem = '0';
-- single_frame
NextCase <= 0;
wait until ProcessDone = AllProcessesDone_c;
-- multi_frame
NextCase <= 1;
wait until ProcessDone = AllProcessesDone_c;
-- timeout
NextCase <= 2;
wait until ProcessDone = AllProcessesDone_c;
-- ts_overflow
NextCase <= 3;
wait until ProcessDone = AllProcessesDone_c;
-- trig_in_posttrig
NextCase <= 4;
wait until ProcessDone = AllProcessesDone_c;
-- always_trig
NextCase <= 5;
wait until ProcessDone = AllProcessesDone_c;
-- backpressure
NextCase <= 6;
wait until ProcessDone = AllProcessesDone_c;
-- modes
NextCase <= 7;
wait until ProcessDone = AllProcessesDone_c;
TbRunning <= false;
wait;
end process;
------------------------------------------------------------
-- Clocks !DO NOT EDIT!
------------------------------------------------------------
p_clock_Str_Clk : process
constant Frequency_c : real := real(125e6);
begin
while TbRunning loop
wait for 0.5*(1 sec)/Frequency_c;
Str_Clk <= not Str_Clk;
end loop;
wait;
end process;
p_clock_ClkSmem : process
constant Frequency_c : real := real(200e6);
begin
while TbRunning loop
wait for 0.5*(1 sec)/Frequency_c;
ClkSmem <= not ClkSmem;
end loop;
wait;
end process;
p_clock_ClkTmem : process
constant Frequency_c : real := real(166e6);
begin
while TbRunning loop
wait for 0.5*(1 sec)/Frequency_c;
ClkTmem <= not ClkTmem;
end loop;
wait;
end process;
------------------------------------------------------------
-- Resets
------------------------------------------------------------
p_rst_Rst : process
begin
wait for 1 us;
-- Wait for two clk edges to ensure reset is active for at least one edge
wait until rising_edge(ClkSmem);
wait until rising_edge(ClkSmem);
RstSmem <= '0';
wait until rising_edge(ClkTmem);
wait until rising_edge(ClkTmem);
RstTmem <= '0';
wait;
end process;
------------------------------------------------------------
-- Processes !DO NOT EDIT!
------------------------------------------------------------
-- *** stream ***
p_stream : process
begin
-- single_frame
wait until NextCase = 0;
ProcessDone(TbProcNr_stream_c) <= '0';
work.psi_ms_daq_input_tb_case_single_frame.stream(Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts, ClkTmem, Arm, IsArmed, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_stream_c) <= '1';
-- multi_frame
wait until NextCase = 1;
ProcessDone(TbProcNr_stream_c) <= '0';
work.psi_ms_daq_input_tb_case_multi_frame.stream(Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts, ClkTmem, Arm, IsArmed, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_stream_c) <= '1';
-- timeout
wait until NextCase = 2;
ProcessDone(TbProcNr_stream_c) <= '0';
work.psi_ms_daq_input_tb_case_timeout.stream(Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts, ClkTmem, Arm, IsArmed, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_stream_c) <= '1';
-- ts_overflow
wait until NextCase = 3;
ProcessDone(TbProcNr_stream_c) <= '0';
work.psi_ms_daq_input_tb_case_ts_overflow.stream(Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts, ClkTmem, Arm, IsArmed, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_stream_c) <= '1';
-- trig_in_posttrig
wait until NextCase = 4;
ProcessDone(TbProcNr_stream_c) <= '0';
work.psi_ms_daq_input_tb_case_trig_in_posttrig.stream(Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts, ClkTmem, Arm, IsArmed, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_stream_c) <= '1';
-- always_trig
wait until NextCase = 5;
ProcessDone(TbProcNr_stream_c) <= '0';
work.psi_ms_daq_input_tb_case_always_trig.stream(Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts, ClkTmem, Arm, IsArmed, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_stream_c) <= '1';
-- backpressure
wait until NextCase = 6;
ProcessDone(TbProcNr_stream_c) <= '0';
work.psi_ms_daq_input_tb_case_backpressure.stream(Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts, ClkTmem, Arm, IsArmed, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_stream_c) <= '1';
-- modes
wait until NextCase = 7;
ProcessDone(TbProcNr_stream_c) <= '0';
work.psi_ms_daq_input_tb_case_modes.stream(Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts, ClkTmem, Arm, IsArmed, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_stream_c) <= '1';
wait;
end process;
-- *** daq ***
p_daq : process
begin
-- single_frame
wait until NextCase = 0;
ProcessDone(TbProcNr_daq_c) <= '0';
work.psi_ms_daq_input_tb_case_single_frame.daq(ClkSmem, PostTrigSpls, Mode, Daq_Vld, Daq_Rdy, Daq_Data, Daq_Level, Daq_HasLast, Ts_Vld, Ts_Rdy, Ts_Data, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_daq_c) <= '1';
-- multi_frame
wait until NextCase = 1;
ProcessDone(TbProcNr_daq_c) <= '0';
work.psi_ms_daq_input_tb_case_multi_frame.daq(ClkSmem, PostTrigSpls, Mode, Daq_Vld, Daq_Rdy, Daq_Data, Daq_Level, Daq_HasLast, Ts_Vld, Ts_Rdy, Ts_Data, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_daq_c) <= '1';
-- timeout
wait until NextCase = 2;
ProcessDone(TbProcNr_daq_c) <= '0';
work.psi_ms_daq_input_tb_case_timeout.daq(ClkSmem, PostTrigSpls, Mode, Daq_Vld, Daq_Rdy, Daq_Data, Daq_Level, Daq_HasLast, Ts_Vld, Ts_Rdy, Ts_Data, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_daq_c) <= '1';
-- ts_overflow
wait until NextCase = 3;
ProcessDone(TbProcNr_daq_c) <= '0';
work.psi_ms_daq_input_tb_case_ts_overflow.daq(ClkSmem, PostTrigSpls, Mode, Daq_Vld, Daq_Rdy, Daq_Data, Daq_Level, Daq_HasLast, Ts_Vld, Ts_Rdy, Ts_Data, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_daq_c) <= '1';
-- trig_in_posttrig
wait until NextCase = 4;
ProcessDone(TbProcNr_daq_c) <= '0';
work.psi_ms_daq_input_tb_case_trig_in_posttrig.daq(ClkSmem, PostTrigSpls, Mode, Daq_Vld, Daq_Rdy, Daq_Data, Daq_Level, Daq_HasLast, Ts_Vld, Ts_Rdy, Ts_Data, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_daq_c) <= '1';
-- always_trig
wait until NextCase = 5;
ProcessDone(TbProcNr_daq_c) <= '0';
work.psi_ms_daq_input_tb_case_always_trig.daq(ClkSmem, PostTrigSpls, Mode, Daq_Vld, Daq_Rdy, Daq_Data, Daq_Level, Daq_HasLast, Ts_Vld, Ts_Rdy, Ts_Data, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_daq_c) <= '1';
-- backpressure
wait until NextCase = 6;
ProcessDone(TbProcNr_daq_c) <= '0';
work.psi_ms_daq_input_tb_case_backpressure.daq(ClkSmem, PostTrigSpls, Mode, Daq_Vld, Daq_Rdy, Daq_Data, Daq_Level, Daq_HasLast, Ts_Vld, Ts_Rdy, Ts_Data, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_daq_c) <= '1';
-- modes
wait until NextCase = 7;
ProcessDone(TbProcNr_daq_c) <= '0';
work.psi_ms_daq_input_tb_case_modes.daq(ClkSmem, PostTrigSpls, Mode, Daq_Vld, Daq_Rdy, Daq_Data, Daq_Level, Daq_HasLast, Ts_Vld, Ts_Rdy, Ts_Data, Generics_c);
wait for 1 ps;
ProcessDone(TbProcNr_daq_c) <= '1';
wait;
end process;
end;

View File

@@ -1,121 +0,0 @@
------------------------------------------------------------
-- Libraries
------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_ms_daq_pkg.all;
library work;
use work.psi_ms_daq_input_tb_pkg.all;
library work;
use work.psi_tb_txt_util.all;
------------------------------------------------------------
-- Package Header
------------------------------------------------------------
package psi_ms_daq_input_tb_case_always_trig is
procedure stream (
signal Str_Clk : in std_logic;
signal Str_Vld : inout std_logic;
signal Str_Rdy : in std_logic;
signal Str_Data : inout std_logic_vector;
signal Str_Trig : inout std_logic;
signal Str_Ts : inout std_logic_vector;
signal Clk : in std_logic;
signal Arm : inout std_logic;
signal IsArmed : in std_logic;
constant Generics_c : Generics_t);
procedure daq (
signal Clk : in std_logic;
signal PostTrigSpls : inout std_logic_vector;
signal Mode : inout RecMode_t;
signal Daq_Vld : in std_logic;
signal Daq_Rdy : inout std_logic;
signal Daq_Data : in Input2Daq_Data_t;
signal Daq_Level : in std_logic_vector;
signal Daq_HasLast : in std_logic;
signal Ts_Vld : in std_logic;
signal Ts_Rdy : inout std_logic;
signal Ts_Data : in std_logic_vector;
constant Generics_c : Generics_t);
end package;
------------------------------------------------------------
-- Package Body
------------------------------------------------------------
package body psi_ms_daq_input_tb_case_always_trig is
procedure stream (
signal Str_Clk : in std_logic;
signal Str_Vld : inout std_logic;
signal Str_Rdy : in std_logic;
signal Str_Data : inout std_logic_vector;
signal Str_Trig : inout std_logic;
signal Str_Ts : inout std_logic_vector;
signal Clk : in std_logic;
signal Arm : inout std_logic;
signal IsArmed : in std_logic;
constant Generics_c : Generics_t) is
begin
-- Wait for config to be applied
print(">> Trigger always set");
wait for 100 ns;
wait until rising_edge(Str_Clk);
-- Apply Input data
Str_Trig <= '1';
Str_Ts <= std_logic_vector(to_unsigned(0, Str_Ts'length));
Str_Vld <= '1';
for SplCnt in 0 to 17 loop
Str_Vld <= '1';
Str_Ts <= std_logic_vector(to_unsigned(SplCnt, Str_Ts'length));
Str_Data <= std_logic_vector(to_unsigned(SplCnt, Generics_c.StreamWidth_g));
wait until rising_edge(Str_Clk);
if Generics_c.VldPulsed_g then
Str_Trig <= '0';
Str_Vld <= '0';
Str_Ts <= std_logic_vector(to_unsigned(0, Str_Ts'length));
Str_Data <= std_logic_vector(to_unsigned(0, Generics_c.StreamWidth_g));
wait until rising_edge(Str_Clk);
end if;
end loop;
Str_Vld <= '0';
Str_Trig <= '0';
Str_Ts <= std_logic_vector(to_unsigned(0, Str_Ts'length));
end procedure;
procedure daq (
signal Clk : in std_logic;
signal PostTrigSpls : inout std_logic_vector;
signal Mode : inout RecMode_t;
signal Daq_Vld : in std_logic;
signal Daq_Rdy : inout std_logic;
signal Daq_Data : in Input2Daq_Data_t;
signal Daq_Level : in std_logic_vector;
signal Daq_HasLast : in std_logic;
signal Ts_Vld : in std_logic;
signal Ts_Rdy : inout std_logic;
signal Ts_Data : in std_logic_vector;
constant Generics_c : Generics_t) is
begin
-- Config
PostTrigSpls <= std_logic_vector(to_unsigned(8, 32));
Daq_Rdy <= '0';
-- Wait until iniput done
wait for 1 us;
wait until rising_edge(Clk);
-- check if frames are recorded back to back without loss
CheckAcqData (9, 0, Generics_c, FrameType_Trigger_c, Clk, Daq_Vld, Daq_Rdy, Daq_Data, Ts_Vld, Ts_Rdy, Ts_Data, false);
CheckAcqData (9, 9, Generics_c, FrameType_Trigger_c, Clk, Daq_Vld, Daq_Rdy, Daq_Data, Ts_Vld, Ts_Rdy, Ts_Data, false, 9);
end procedure;
end;

View File

@@ -1,162 +0,0 @@
------------------------------------------------------------
-- Libraries
------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_ms_daq_pkg.all;
library work;
use work.psi_ms_daq_input_tb_pkg.all;
library work;
use work.psi_tb_txt_util.all;
------------------------------------------------------------
-- Package Header
------------------------------------------------------------
package psi_ms_daq_input_tb_case_backpressure is
procedure stream (
signal Str_Clk : in std_logic;
signal Str_Vld : inout std_logic;
signal Str_Rdy : in std_logic;
signal Str_Data : inout std_logic_vector;
signal Str_Trig : inout std_logic;
signal Str_Ts : inout std_logic_vector;
signal Clk : in std_logic;
signal Arm : inout std_logic;
signal IsArmed : in std_logic;
constant Generics_c : Generics_t);
procedure daq (
signal Clk : in std_logic;
signal PostTrigSpls : inout std_logic_vector;
signal Mode : inout RecMode_t;
signal Daq_Vld : in std_logic;
signal Daq_Rdy : inout std_logic;
signal Daq_Data : in Input2Daq_Data_t;
signal Daq_Level : in std_logic_vector;
signal Daq_HasLast : in std_logic;
signal Ts_Vld : in std_logic;
signal Ts_Rdy : inout std_logic;
signal Ts_Data : in std_logic_vector;
constant Generics_c : Generics_t);
shared variable Samples_v : integer := 0;
shared variable StartReading_v : boolean := false;
shared variable ReadingStarted_v : boolean := false;
end package;
------------------------------------------------------------
-- Package Body
------------------------------------------------------------
package body psi_ms_daq_input_tb_case_backpressure is
procedure stream (
signal Str_Clk : in std_logic;
signal Str_Vld : inout std_logic;
signal Str_Rdy : in std_logic;
signal Str_Data : inout std_logic_vector;
signal Str_Trig : inout std_logic;
signal Str_Ts : inout std_logic_vector;
signal Clk : in std_logic;
signal Arm : inout std_logic;
signal IsArmed : in std_logic;
constant Generics_c : Generics_t) is
begin
-- Wait for config to be applied
print(">> Test Back-Pressure Handling");
wait for 100 ns;
wait until rising_edge(Str_Clk);
-- Apply samples until the data FIFO is full
-- Apply Input data
Str_Trig <= '0';
Str_Ts <= std_logic_vector(to_unsigned(0, Str_Ts'length));
while Str_Rdy = '1' loop
Str_Vld <= '1';
Str_Data <= std_logic_vector(to_unsigned(Samples_v, Generics_c.StreamWidth_g));
Samples_v := Samples_v + 1;
wait until rising_edge(Str_Clk);
wait for 1 ns;
if Generics_c.VldPulsed_g then
Str_Vld <= '0';
Str_Data <= std_logic_vector(to_unsigned(0, Generics_c.StreamWidth_g));
wait until rising_edge(Str_Clk);
end if;
end loop;
-- Keep valid 10 more cycles
Str_Vld <= '1';
for i in 0 to 9 loop
wait until rising_edge(Str_Clk);
end loop;
Str_Vld <= '0';
-- Apply Trigger
wait until rising_edge(Str_Clk);
Str_Trig <= '1';
Str_Ts <= std_logic_vector(to_unsigned(101, Str_Ts'length));
wait until rising_edge(Str_Clk);
Str_Trig <= '0';
Str_Ts <= std_logic_vector(to_unsigned(0, Str_Ts'length));
-- Add some more invalid samples
Str_Vld <= '1';
for i in 0 to 9 loop
wait until rising_edge(Str_Clk);
end loop;
Str_Vld <= '0';
StartReading_v := true;
while not ReadingStarted_v loop
wait until rising_edge(Str_Clk);
end loop;
-- Apply 9 more samples (trigger + 8 post-trig)
Str_Vld <= '1';
for i in 0 to 8 loop
Str_Data <= std_logic_vector(to_unsigned(Samples_v, Generics_c.StreamWidth_g));
wait until rising_edge(Str_Clk) and Str_Rdy = '1';
Samples_v := Samples_v + 1;
end loop;
Str_Vld <= '0';
end procedure;
procedure daq (
signal Clk : in std_logic;
signal PostTrigSpls : inout std_logic_vector;
signal Mode : inout RecMode_t;
signal Daq_Vld : in std_logic;
signal Daq_Rdy : inout std_logic;
signal Daq_Data : in Input2Daq_Data_t;
signal Daq_Level : in std_logic_vector;
signal Daq_HasLast : in std_logic;
signal Ts_Vld : in std_logic;
signal Ts_Rdy : inout std_logic;
signal Ts_Data : in std_logic_vector;
constant Generics_c : Generics_t) is
begin
-- Config
PostTrigSpls <= std_logic_vector(to_unsigned(8, 32));
Daq_Rdy <= '0';
-- Check result
while not StartReading_v loop
wait until rising_edge(Clk);
end loop;
ReadingStarted_v := true;
CheckAcqData (Samples_v+9, 101, Generics_c, FrameType_Trigger_c, Clk, Daq_Vld, Daq_Rdy, Daq_Data, Ts_Vld, Ts_Rdy, Ts_Data);
end procedure;
end;

View File

@@ -1,183 +0,0 @@
------------------------------------------------------------
-- Libraries
------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_ms_daq_pkg.all;
library work;
use work.psi_ms_daq_input_tb_pkg.all;
library work;
use work.psi_tb_txt_util.all;
use work.psi_tb_compare_pkg.all;
use work.psi_tb_activity_pkg.all;
------------------------------------------------------------
-- Package Header
------------------------------------------------------------
package psi_ms_daq_input_tb_case_modes is
procedure stream (
signal Str_Clk : in std_logic;
signal Str_Vld : inout std_logic;
signal Str_Rdy : in std_logic;
signal Str_Data : inout std_logic_vector;
signal Str_Trig : inout std_logic;
signal Str_Ts : inout std_logic_vector;
signal Clk : in std_logic;
signal Arm : inout std_logic;
signal IsArmed : in std_logic;
constant Generics_c : Generics_t);
procedure daq (
signal Clk : in std_logic;
signal PostTrigSpls : inout std_logic_vector;
signal Mode : inout RecMode_t;
signal Daq_Vld : in std_logic;
signal Daq_Rdy : inout std_logic;
signal Daq_Data : in Input2Daq_Data_t;
signal Daq_Level : in std_logic_vector;
signal Daq_HasLast : in std_logic;
signal Ts_Vld : in std_logic;
signal Ts_Rdy : inout std_logic;
signal Ts_Data : in std_logic_vector;
constant Generics_c : Generics_t);
shared variable TestCase : integer := -1;
shared variable StrDone : boolean := false;
end package;
------------------------------------------------------------
-- Package Body
------------------------------------------------------------
package body psi_ms_daq_input_tb_case_modes is
procedure stream (
signal Str_Clk : in std_logic;
signal Str_Vld : inout std_logic;
signal Str_Rdy : in std_logic;
signal Str_Data : inout std_logic_vector;
signal Str_Trig : inout std_logic;
signal Str_Ts : inout std_logic_vector;
signal Clk : in std_logic;
signal Arm : inout std_logic;
signal IsArmed : in std_logic;
constant Generics_c : Generics_t) is
begin
-- Trigger Mask Mode
while TestCase /= 0 loop
wait until rising_edge(Str_Clk);
end loop;
wait for 100 ns;
-- Recorded but trigger lost
ApplyStrData(5, 1, 1, Generics_c, Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts);
-- Received
PulseSig(Arm, Clk);
wait for 100 ns;
ApplyStrData(4, 0, 2, Generics_c, Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts, 5);
-- Lost
ApplyStrData(7, 3, 3, Generics_c, Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts);
StrDone := true;
-- Single Shot Mode
while TestCase /= 1 loop
wait until rising_edge(Str_Clk);
end loop;
wait for 100 ns;
-- Lost
ApplyStrData(5, 1, 1, Generics_c, Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts);
-- Received
PulseSig(Arm, Clk);
wait for 100 ns;
ApplyStrData(6, 2, 2, Generics_c, Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts, 5);
-- Lost
ApplyStrData(7, 3, 3, Generics_c, Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts, 5+6);
StrDone := true;
-- Manual Mode
while TestCase /= 2 loop
wait until rising_edge(Str_Clk);
end loop;
wait for 100 ns;
-- Lost
ApplyStrData(5, 1, 1, Generics_c, Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts);
-- Received (partially)
Str_Ts <= std_logic_vector(to_unsigned(10, 64));
PulseSig(Arm, Clk);
wait for 100 ns;
Str_Ts <= std_logic_vector(to_unsigned(0, 64));
ApplyStrData(100, 80, 2, Generics_c, Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts, 5);
-- Lost
ApplyStrData(7, 3, 3, Generics_c, Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts, 5+6);
StrDone := true;
end procedure;
procedure daq (
signal Clk : in std_logic;
signal PostTrigSpls : inout std_logic_vector;
signal Mode : inout RecMode_t;
signal Daq_Vld : in std_logic;
signal Daq_Rdy : inout std_logic;
signal Daq_Data : in Input2Daq_Data_t;
signal Daq_Level : in std_logic_vector;
signal Daq_HasLast : in std_logic;
signal Ts_Vld : in std_logic;
signal Ts_Rdy : inout std_logic;
signal Ts_Data : in std_logic_vector;
constant Generics_c : Generics_t) is
begin
-- Config
PostTrigSpls <= std_logic_vector(to_unsigned(3, 32));
Daq_Rdy <= '0';
-- Trigger Mask Mode
print(">> Trigger Mask Mode");
StrDone := false;
Mode <= RecMode_TriggerMask_c;
TestCase := 0;
CheckAcqData (5+4, 2, Generics_c, FrameType_Trigger_c, Clk, Daq_Vld, Daq_Rdy, Daq_Data, Ts_Vld, Ts_Rdy, Ts_Data);
wait for 100 ns;
CheckAcqData (7, 3, Generics_c, FrameType_Timeout_c, Clk, Daq_Vld, Daq_Rdy, Daq_Data, Ts_Vld, Ts_Rdy, Ts_Data);
while not StrDone loop
wait until rising_edge(Clk);
end loop;
wait until rising_edge(Clk);
StdlCompare(0, Daq_Vld, "Unexpected data is available");
-- Single Shot Mode
print(">> Single Shot Mode");
StrDone := false;
Mode <= RecMode_SingleShot_c;
TestCase := 1;
CheckAcqData (6, 2, Generics_c, FrameType_Trigger_c, Clk, Daq_Vld, Daq_Rdy, Daq_Data, Ts_Vld, Ts_Rdy, Ts_Data, false, 5);
while not StrDone loop
wait until rising_edge(Clk);
end loop;
wait until rising_edge(Clk);
StdlCompare(0, Daq_Vld, "Unexpected data is available");
-- Manual Mode
PostTrigSpls <= std_logic_vector(to_unsigned(6, 32));
print(">> Manual Mode");
StrDone := false;
Mode <= RecMode_ManuelMode_c;
TestCase := 2;
CheckAcqData (7, 10, Generics_c, FrameType_Trigger_c, Clk, Daq_Vld, Daq_Rdy, Daq_Data, Ts_Vld, Ts_Rdy, Ts_Data, false, 5);
while not StrDone loop
wait until rising_edge(Clk);
end loop;
wait until rising_edge(Clk);
StdlCompare(0, Daq_Vld, "Unexpected data is available");
end procedure;
end;

View File

@@ -1,112 +0,0 @@
------------------------------------------------------------
-- Libraries
------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_ms_daq_pkg.all;
library work;
use work.psi_ms_daq_input_tb_pkg.all;
library work;
use work.psi_tb_txt_util.all;
------------------------------------------------------------
-- Package Header
------------------------------------------------------------
package psi_ms_daq_input_tb_case_multi_frame is
procedure stream (
signal Str_Clk : in std_logic;
signal Str_Vld : inout std_logic;
signal Str_Rdy : in std_logic;
signal Str_Data : inout std_logic_vector;
signal Str_Trig : inout std_logic;
signal Str_Ts : inout std_logic_vector;
signal Clk : in std_logic;
signal Arm : inout std_logic;
signal IsArmed : in std_logic;
constant Generics_c : Generics_t);
procedure daq (
signal Clk : in std_logic;
signal PostTrigSpls : inout std_logic_vector;
signal Mode : inout RecMode_t;
signal Daq_Vld : in std_logic;
signal Daq_Rdy : inout std_logic;
signal Daq_Data : in Input2Daq_Data_t;
signal Daq_Level : in std_logic_vector;
signal Daq_HasLast : in std_logic;
signal Ts_Vld : in std_logic;
signal Ts_Rdy : inout std_logic;
signal Ts_Data : in std_logic_vector;
constant Generics_c : Generics_t);
shared variable ThreeFramesDone : boolean := false;
end package;
------------------------------------------------------------
-- Package Body
------------------------------------------------------------
package body psi_ms_daq_input_tb_case_multi_frame is
procedure stream (
signal Str_Clk : in std_logic;
signal Str_Vld : inout std_logic;
signal Str_Rdy : in std_logic;
signal Str_Data : inout std_logic_vector;
signal Str_Trig : inout std_logic;
signal Str_Ts : inout std_logic_vector;
signal Clk : in std_logic;
signal Arm : inout std_logic;
signal IsArmed : in std_logic;
constant Generics_c : Generics_t) is
begin
-- Wait for config to be applied
wait for 100 ns;
wait until rising_edge(Str_Clk);
-- Apply five Frames
print(">> Multi-Frame");
ApplyStrData(5, 1, 1, Generics_c, Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts);
ApplyStrData(4, 0, 2, Generics_c, Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts);
ApplyStrData(7, 3, 3, Generics_c, Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts);
ThreeFramesDone := true;
ApplyStrData(14, 10, 4, Generics_c, Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts);
ApplyStrData(15, 11, 5, Generics_c, Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts);
end procedure;
procedure daq (
signal Clk : in std_logic;
signal PostTrigSpls : inout std_logic_vector;
signal Mode : inout RecMode_t;
signal Daq_Vld : in std_logic;
signal Daq_Rdy : inout std_logic;
signal Daq_Data : in Input2Daq_Data_t;
signal Daq_Level : in std_logic_vector;
signal Daq_HasLast : in std_logic;
signal Ts_Vld : in std_logic;
signal Ts_Rdy : inout std_logic;
signal Ts_Data : in std_logic_vector;
constant Generics_c : Generics_t) is
begin
-- Config
PostTrigSpls <= std_logic_vector(to_unsigned(3, 32));
Daq_Rdy <= '0';
-- Wait until first two frames are fully received
while not ThreeFramesDone loop
wait until rising_edge(Clk);
end loop;
CheckAcqData (5, 1, Generics_c, FrameType_Trigger_c, Clk, Daq_Vld, Daq_Rdy, Daq_Data, Ts_Vld, Ts_Rdy, Ts_Data);
CheckAcqData (4, 2, Generics_c, FrameType_Trigger_c, Clk, Daq_Vld, Daq_Rdy, Daq_Data, Ts_Vld, Ts_Rdy, Ts_Data);
CheckAcqData (7, 3, Generics_c, FrameType_Trigger_c, Clk, Daq_Vld, Daq_Rdy, Daq_Data, Ts_Vld, Ts_Rdy, Ts_Data);
CheckAcqData (14, 4, Generics_c, FrameType_Trigger_c, Clk, Daq_Vld, Daq_Rdy, Daq_Data, Ts_Vld, Ts_Rdy, Ts_Data);
CheckAcqData (15, 5, Generics_c, FrameType_Trigger_c, Clk, Daq_Vld, Daq_Rdy, Daq_Data, Ts_Vld, Ts_Rdy, Ts_Data);
end procedure;
end;

View File

@@ -1,182 +0,0 @@
------------------------------------------------------------
-- Libraries
------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_ms_daq_pkg.all;
library work;
use work.psi_ms_daq_input_tb_pkg.all;
library work;
use work.psi_tb_txt_util.all;
------------------------------------------------------------
-- Package Header
------------------------------------------------------------
package psi_ms_daq_input_tb_case_single_frame is
procedure stream (
signal Str_Clk : in std_logic;
signal Str_Vld : inout std_logic;
signal Str_Rdy : in std_logic;
signal Str_Data : inout std_logic_vector;
signal Str_Trig : inout std_logic;
signal Str_Ts : inout std_logic_vector;
signal Clk : in std_logic;
signal Arm : inout std_logic;
signal IsArmed : in std_logic;
constant Generics_c : Generics_t);
procedure daq (
signal Clk : in std_logic;
signal PostTrigSpls : inout std_logic_vector;
signal Mode : inout RecMode_t;
signal Daq_Vld : in std_logic;
signal Daq_Rdy : inout std_logic;
signal Daq_Data : in Input2Daq_Data_t;
signal Daq_Level : in std_logic_vector;
signal Daq_HasLast : in std_logic;
signal Ts_Vld : in std_logic;
signal Ts_Rdy : inout std_logic;
signal Ts_Data : in std_logic_vector;
constant Generics_c : Generics_t);
shared variable CheckDone_v : boolean := false;
shared variable Samples_v : integer;
end package;
------------------------------------------------------------
-- Package Body
------------------------------------------------------------
package body psi_ms_daq_input_tb_case_single_frame is
procedure stream (
signal Str_Clk : in std_logic;
signal Str_Vld : inout std_logic;
signal Str_Rdy : in std_logic;
signal Str_Data : inout std_logic_vector;
signal Str_Trig : inout std_logic;
signal Str_Ts : inout std_logic_vector;
signal Clk : in std_logic;
signal Arm : inout std_logic;
signal IsArmed : in std_logic;
constant Generics_c : Generics_t) is
begin
-- Wait for config to be applied
wait for 100 ns;
wait until rising_edge(Str_Clk);
-- Single 3 QWORD frame, trigger at the end
print(">> Single 3 QWORD frame, trigger at the end");
Samples_v := 3*64/Generics_c.StreamWidth_g;
ApplyStrData(Samples_v, Samples_v-1, 100, Generics_c, Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts);
while not CheckDone_v loop
wait until rising_edge(Str_Clk);
end loop;
CheckDone_v := false;
-- Frame shortened by trigger
if Generics_c.StreamWidth_g /= 64 then
print(">> Frame shortened by trigger");
Samples_v := 3*64/Generics_c.StreamWidth_g - 1;
ApplyStrData(Samples_v, Samples_v-1, 101, Generics_c, Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts);
while not CheckDone_v loop
wait until rising_edge(Str_Clk);
end loop;
CheckDone_v := false;
end if;
-- Single Sample Frame
print(">> Single sample frame");
Samples_v := 1;
ApplyStrData(Samples_v, Samples_v-1, 102, Generics_c, Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts);
while not CheckDone_v loop
wait until rising_edge(Str_Clk);
end loop;
CheckDone_v := false;
-- 5 Samples, 3 Post Trigger
print(">> 5 Samples, 3 Post Trigger");
wait for 100 ns;
Samples_v := 5;
ApplyStrData(5, 1, 103, Generics_c, Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts);
while not CheckDone_v loop
wait until rising_edge(Str_Clk);
end loop;
CheckDone_v := false;
-- 5 Samples, 1 Post Trigger
print(">> 5 Samples, 1 Post Trigger");
wait for 100 ns;
Samples_v := 5;
ApplyStrData(5, 3, 104, Generics_c, Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts);
while not CheckDone_v loop
wait until rising_edge(Str_Clk);
end loop;
CheckDone_v := false;
end procedure;
procedure daq (
signal Clk : in std_logic;
signal PostTrigSpls : inout std_logic_vector;
signal Mode : inout RecMode_t;
signal Daq_Vld : in std_logic;
signal Daq_Rdy : inout std_logic;
signal Daq_Data : in Input2Daq_Data_t;
signal Daq_Level : in std_logic_vector;
signal Daq_HasLast : in std_logic;
signal Ts_Vld : in std_logic;
signal Ts_Rdy : inout std_logic;
signal Ts_Data : in std_logic_vector;
constant Generics_c : Generics_t) is
begin
-- Config
PostTrigSpls <= std_logic_vector(to_unsigned(0, 32));
Daq_Rdy <= '0';
-- Single 3 QWORD frame, trigger at the end
wait for 1 us;
assert unsigned(Daq_Level) = 3 report "###ERROR###: 3QW, Trigger at end: Level incorrect" severity error;
assert Daq_HasLast = '1' report "###ERROR###: 3QW, Trigger at end: HastTlast incorrect" severity error;
CheckAcqData (Samples_v, 100, Generics_c, FrameType_Trigger_c, Clk, Daq_Vld, Daq_Rdy, Daq_Data, Ts_Vld, Ts_Rdy, Ts_Data);
CheckDone_v := true;
-- Frame shortened by trigger
wait for 1 us;
if Generics_c.StreamWidth_g /= 64 then
assert unsigned(Daq_Level) = 3 report "###ERROR###: Shortened: Level incorrect" severity error;
assert Daq_HasLast = '1' report "###ERROR###: Shortened: HastTlast incorrect" severity error;
CheckAcqData (Samples_v, 101, Generics_c, FrameType_Trigger_c, Clk, Daq_Vld, Daq_Rdy, Daq_Data, Ts_Vld, Ts_Rdy, Ts_Data);
CheckDone_v := true;
end if;
-- Single Sample Frame
wait for 1 us;
assert unsigned(Daq_Level) = 1 report "###ERROR###: Single Sample: Level incorrect" severity error;
assert Daq_HasLast = '1' report "###ERROR###: Single Sample: HastTlast incorrect" severity error;
CheckAcqData (Samples_v, 102, Generics_c, FrameType_Trigger_c, Clk, Daq_Vld, Daq_Rdy, Daq_Data, Ts_Vld, Ts_Rdy, Ts_Data);
CheckDone_v := true;
-- 5 Samples, 3 Post Trigger
PostTrigSpls <= std_logic_vector(to_unsigned(3, 32));
wait for 1 us;
assert Daq_HasLast = '1' report "###ERROR###: 5 Samples 3 Post, Trigger at end: HastTlast incorrect" severity error;
CheckAcqData (5, 103, Generics_c, FrameType_Trigger_c, Clk, Daq_Vld, Daq_Rdy, Daq_Data, Ts_Vld, Ts_Rdy, Ts_Data);
CheckDone_v := true;
-- 5 Samples, 1 Post Trigger
PostTrigSpls <= std_logic_vector(to_unsigned(1, 32));
wait for 1 us;
assert Daq_HasLast = '1' report "###ERROR###: 5 Samples 1 Post, Trigger at end: HastTlast incorrect" severity error;
CheckAcqData (5, 104, Generics_c, FrameType_Trigger_c, Clk, Daq_Vld, Daq_Rdy, Daq_Data, Ts_Vld, Ts_Rdy, Ts_Data);
CheckDone_v := true;
end procedure;
end;

View File

@@ -1,139 +0,0 @@
------------------------------------------------------------
-- Libraries
------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_ms_daq_pkg.all;
library work;
use work.psi_ms_daq_input_tb_pkg.all;
library work;
use work.psi_tb_txt_util.all;
use work.psi_tb_compare_pkg.all;
------------------------------------------------------------
-- Package Header
------------------------------------------------------------
package psi_ms_daq_input_tb_case_timeout is
procedure stream (
signal Str_Clk : in std_logic;
signal Str_Vld : inout std_logic;
signal Str_Rdy : in std_logic;
signal Str_Data : inout std_logic_vector;
signal Str_Trig : inout std_logic;
signal Str_Ts : inout std_logic_vector;
signal Clk : in std_logic;
signal Arm : inout std_logic;
signal IsArmed : in std_logic;
constant Generics_c : Generics_t);
procedure daq (
signal Clk : in std_logic;
signal PostTrigSpls : inout std_logic_vector;
signal Mode : inout RecMode_t;
signal Daq_Vld : in std_logic;
signal Daq_Rdy : inout std_logic;
signal Daq_Data : in Input2Daq_Data_t;
signal Daq_Level : in std_logic_vector;
signal Daq_HasLast : in std_logic;
signal Ts_Vld : in std_logic;
signal Ts_Rdy : inout std_logic;
signal Ts_Data : in std_logic_vector;
constant Generics_c : Generics_t);
shared variable CheckDone_v : boolean := false;
end package;
------------------------------------------------------------
-- Package Body
------------------------------------------------------------
package body psi_ms_daq_input_tb_case_timeout is
procedure stream (
signal Str_Clk : in std_logic;
signal Str_Vld : inout std_logic;
signal Str_Rdy : in std_logic;
signal Str_Data : inout std_logic_vector;
signal Str_Trig : inout std_logic;
signal Str_Ts : inout std_logic_vector;
signal Clk : in std_logic;
signal Arm : inout std_logic;
signal IsArmed : in std_logic;
constant Generics_c : Generics_t) is
begin
-- Wait for config to be applied
wait for 100 ns;
wait until rising_edge(Str_Clk);
-- Apply 11 samples and then wait for timeout
print(">> Timeout - After odd number of samples");
ApplyStrData(11, 1000, 1, Generics_c, Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts);
wait until rising_edge(Str_Clk);
while not CheckDone_v loop
wait until rising_edge(Str_Clk);
end loop;
CheckDone_v := false;
-- Apply 16 samples and then wait for timeout
print(">> Timeout - After even number of samples");
ApplyStrData(16, 1000, 2, Generics_c, Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts);
wait until rising_edge(Str_Clk);
while not CheckDone_v loop
wait until rising_edge(Str_Clk);
end loop;
CheckDone_v := false;
end procedure;
procedure daq (
signal Clk : in std_logic;
signal PostTrigSpls : inout std_logic_vector;
signal Mode : inout RecMode_t;
signal Daq_Vld : in std_logic;
signal Daq_Rdy : inout std_logic;
signal Daq_Data : in Input2Daq_Data_t;
signal Daq_Level : in std_logic_vector;
signal Daq_HasLast : in std_logic;
signal Ts_Vld : in std_logic;
signal Ts_Rdy : inout std_logic;
signal Ts_Data : in std_logic_vector;
constant Generics_c : Generics_t) is
begin
-- Config
PostTrigSpls <= std_logic_vector(to_unsigned(3, 32));
Daq_Rdy <= '0';
-- *** Timeout - After odd number of samples ***
-- Check if no data is available prior to the timeout
wait for StreamTimeout_g*(1 sec) - 1 us;
wait until rising_edge(Clk);
StdlCompare(0, Daq_HasLast, "HastTlast asserted unexpectedly");
-- Check data after timeout
wait for 2 us;
wait until rising_edge(Clk);
CheckAcqData (11, 1, Generics_c, FrameType_Timeout_c, Clk, Daq_Vld, Daq_Rdy, Daq_Data, Ts_Vld, Ts_Rdy, Ts_Data);
CheckDone_v := true;
-- *** Timeout - After even number of samples ***
-- Check if no data is available prior to the timeout
wait for StreamTimeout_g*(1 sec) - 1 us;
wait until rising_edge(Clk);
StdlCompare(0, Daq_HasLast, "HastTlast asserted unexpectedly");
-- Check data after timeout
wait for 2 us;
wait until rising_edge(Clk);
CheckAcqData (16, 2, Generics_c, FrameType_Timeout_c, Clk, Daq_Vld, Daq_Rdy, Daq_Data, Ts_Vld, Ts_Rdy, Ts_Data);
CheckDone_v := true;
end procedure;
end;

View File

@@ -1,129 +0,0 @@
------------------------------------------------------------
-- Libraries
------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_ms_daq_pkg.all;
library work;
use work.psi_ms_daq_input_tb_pkg.all;
library work;
use work.psi_tb_txt_util.all;
use work.psi_tb_compare_pkg.all;
------------------------------------------------------------
-- Package Header
------------------------------------------------------------
package psi_ms_daq_input_tb_case_trig_in_posttrig is
procedure stream (
signal Str_Clk : in std_logic;
signal Str_Vld : inout std_logic;
signal Str_Rdy : in std_logic;
signal Str_Data : inout std_logic_vector;
signal Str_Trig : inout std_logic;
signal Str_Ts : inout std_logic_vector;
signal Clk : in std_logic;
signal Arm : inout std_logic;
signal IsArmed : in std_logic;
constant Generics_c : Generics_t);
procedure daq (
signal Clk : in std_logic;
signal PostTrigSpls : inout std_logic_vector;
signal Mode : inout RecMode_t;
signal Daq_Vld : in std_logic;
signal Daq_Rdy : inout std_logic;
signal Daq_Data : in Input2Daq_Data_t;
signal Daq_Level : in std_logic_vector;
signal Daq_HasLast : in std_logic;
signal Ts_Vld : in std_logic;
signal Ts_Rdy : inout std_logic;
signal Ts_Data : in std_logic_vector;
constant Generics_c : Generics_t);
shared variable CheckDone_v : boolean := false;
end package;
------------------------------------------------------------
-- Package Body
------------------------------------------------------------
package body psi_ms_daq_input_tb_case_trig_in_posttrig is
procedure stream (
signal Str_Clk : in std_logic;
signal Str_Vld : inout std_logic;
signal Str_Rdy : in std_logic;
signal Str_Data : inout std_logic_vector;
signal Str_Trig : inout std_logic;
signal Str_Ts : inout std_logic_vector;
signal Clk : in std_logic;
signal Arm : inout std_logic;
signal IsArmed : in std_logic;
constant Generics_c : Generics_t) is
begin
-- Wait for config to be applied
print(">> Trigger in Post Trigger (with space)");
wait for 100 ns;
wait until rising_edge(Str_Clk);
-- Create frame which has a trigger inside the post-trigger period
ApplyStrData(10, 4, 100, Generics_c, Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts);
ApplyStrData(3, 1, 101, Generics_c, Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts, 10);
-- Create frame which has a trigger that is longer than one period
while not CheckDone_v loop
wait until rising_edge(Str_Clk);
end loop;
CheckDone_v := false;
ApplyStrData(5, 4, 100, Generics_c, Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts);
ApplyStrData(8, 0, 101, Generics_c, Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts, 5);
end procedure;
procedure daq (
signal Clk : in std_logic;
signal PostTrigSpls : inout std_logic_vector;
signal Mode : inout RecMode_t;
signal Daq_Vld : in std_logic;
signal Daq_Rdy : inout std_logic;
signal Daq_Data : in Input2Daq_Data_t;
signal Daq_Level : in std_logic_vector;
signal Daq_HasLast : in std_logic;
signal Ts_Vld : in std_logic;
signal Ts_Rdy : inout std_logic;
signal Ts_Data : in std_logic_vector;
constant Generics_c : Generics_t) is
begin
-- Config
PostTrigSpls <= std_logic_vector(to_unsigned(8, 32));
Daq_Rdy <= '0';
-- Check trigger in post-trigger with space
wait for 1 us;
CheckAcqData (13, 100, Generics_c, FrameType_Trigger_c, Clk, Daq_Vld, Daq_Rdy, Daq_Data, Ts_Vld, Ts_Rdy, Ts_Data);
StdlvCompareInt(0, Daq_Level, "Trig in Posttrig (space): Level incorrect", false);
StdlCompare(0, Daq_HasLast, "Trig in Posttrig (space): HastTlast incorrec");
StdlCompare(0, Ts_Vld, "Trig in Posttrig (space): Ts_Vld incorrect");
CheckDone_v := true;
-- Check trigger in post-trigger back to back
wait for 1 us;
CheckAcqData (13, 100, Generics_c, FrameType_Trigger_c, Clk, Daq_Vld, Daq_Rdy, Daq_Data, Ts_Vld, Ts_Rdy, Ts_Data);
StdlvCompareInt(0, Daq_Level, "Trig in Posttrig (back-to-back): Level incorrect", false);
StdlCompare(0, Daq_HasLast, "Trig in Posttrig (back-to-back): HastTlast incorrec");
StdlCompare(0, Ts_Vld, "Trig in Posttrig (back-to-back): Ts_Vld incorrect");
CheckDone_v := true;
end procedure;
end;

View File

@@ -1,156 +0,0 @@
------------------------------------------------------------
-- Libraries
------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_ms_daq_pkg.all;
library work;
use work.psi_ms_daq_input_tb_pkg.all;
library work;
use work.psi_tb_txt_util.all;
------------------------------------------------------------
-- Package Header
------------------------------------------------------------
package psi_ms_daq_input_tb_case_ts_overflow is
procedure stream (
signal Str_Clk : in std_logic;
signal Str_Vld : inout std_logic;
signal Str_Rdy : in std_logic;
signal Str_Data : inout std_logic_vector;
signal Str_Trig : inout std_logic;
signal Str_Ts : inout std_logic_vector;
signal Clk : in std_logic;
signal Arm : inout std_logic;
signal IsArmed : in std_logic;
constant Generics_c : Generics_t);
procedure daq (
signal Clk : in std_logic;
signal PostTrigSpls : inout std_logic_vector;
signal Mode : inout RecMode_t;
signal Daq_Vld : in std_logic;
signal Daq_Rdy : inout std_logic;
signal Daq_Data : in Input2Daq_Data_t;
signal Daq_Level : in std_logic_vector;
signal Daq_HasLast : in std_logic;
signal Ts_Vld : in std_logic;
signal Ts_Rdy : inout std_logic;
signal Ts_Data : in std_logic_vector;
constant Generics_c : Generics_t);
shared variable StrDone_v : boolean := false;
shared variable CheckDone_v : boolean := false;
end package;
------------------------------------------------------------
-- Package Body
------------------------------------------------------------
package body psi_ms_daq_input_tb_case_ts_overflow is
procedure stream (
signal Str_Clk : in std_logic;
signal Str_Vld : inout std_logic;
signal Str_Rdy : in std_logic;
signal Str_Data : inout std_logic_vector;
signal Str_Trig : inout std_logic;
signal Str_Ts : inout std_logic_vector;
signal Clk : in std_logic;
signal Arm : inout std_logic;
signal IsArmed : in std_logic;
constant Generics_c : Generics_t) is
begin
-- Wait for config to be applied
print(">> TS FIFO Overflow");
wait for 100 ns;
wait until rising_edge(Str_Clk);
-- Provoke TS Fifo Overflow
for i in 0 to StreamTsFifoDepth_g-1 loop
ApplyStrData(2, 1, i, Generics_c, Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts);
end loop;
StrDone_v := true;
-- Add two frames frame while timestamp FIFO is in overflow condition
while not CheckDone_v loop
wait until rising_edge(Str_Clk);
end loop;
CheckDone_v := false;
ApplyStrData(2, 1, 100, Generics_c, Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts);
ApplyStrData(2, 1, 101, Generics_c, Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts);
StrDone_v := true;
-- Add two good frames to check recovery
while not CheckDone_v loop
wait until rising_edge(Str_Clk);
end loop;
CheckDone_v := false;
ApplyStrData(2, 1, 1000, Generics_c, Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts);
ApplyStrData(2, 1, 1001, Generics_c, Str_Clk, Str_Vld, Str_Rdy, Str_Data, Str_Trig, Str_Ts);
StrDone_v := true;
end procedure;
procedure daq (
signal Clk : in std_logic;
signal PostTrigSpls : inout std_logic_vector;
signal Mode : inout RecMode_t;
signal Daq_Vld : in std_logic;
signal Daq_Rdy : inout std_logic;
signal Daq_Data : in Input2Daq_Data_t;
signal Daq_Level : in std_logic_vector;
signal Daq_HasLast : in std_logic;
signal Ts_Vld : in std_logic;
signal Ts_Rdy : inout std_logic;
signal Ts_Data : in std_logic_vector;
constant Generics_c : Generics_t) is
begin
-- Config
PostTrigSpls <= std_logic_vector(to_unsigned(0, 32));
Daq_Rdy <= '0';
-- After provoking overflow, read three frames to free space in TS FIFO (to check if this does not have effect until data FIFO empty)
while not StrDone_v loop
wait until rising_edge(Clk);
end loop;
StrDone_v := false;
CheckAcqData (2, 0, Generics_c, FrameType_Trigger_c, Clk, Daq_Vld, Daq_Rdy, Daq_Data, Ts_Vld, Ts_Rdy, Ts_Data);
CheckAcqData (2, 1, Generics_c, FrameType_Trigger_c, Clk, Daq_Vld, Daq_Rdy, Daq_Data, Ts_Vld, Ts_Rdy, Ts_Data);
CheckAcqData (2, 2, Generics_c, FrameType_Trigger_c, Clk, Daq_Vld, Daq_Rdy, Daq_Data, Ts_Vld, Ts_Rdy, Ts_Data);
CheckDone_v := true;
-- Read remaining good frames
while not StrDone_v loop
wait until rising_edge(Clk);
end loop;
StrDone_v := false;
for i in 3 to StreamTsFifoDepth_g-2 loop
CheckAcqData (2, i, Generics_c, FrameType_Trigger_c, Clk, Daq_Vld, Daq_Rdy, Daq_Data, Ts_Vld, Ts_Rdy, Ts_Data);
end loop;
-- Read bad frames
for i in 0 to 2 loop
CheckAcqData (2, -1, Generics_c, FrameType_Trigger_c, Clk, Daq_Vld, Daq_Rdy, Daq_Data, Ts_Vld, Ts_Rdy, Ts_Data, True);
end loop;
wait for 1 us; -- leave some time since recovery requires some clock cycles of empty TS FIFO and not triggers in Data FIFO
CheckDone_v := true;
-- Check two good frames to check recovery
while not StrDone_v loop
wait until rising_edge(Clk);
end loop;
StrDone_v := false;
CheckAcqData (2, 1000, Generics_c, FrameType_Trigger_c, Clk, Daq_Vld, Daq_Rdy, Daq_Data, Ts_Vld, Ts_Rdy, Ts_Data);
CheckAcqData (2, 1001, Generics_c, FrameType_Trigger_c, Clk, Daq_Vld, Daq_Rdy, Daq_Data, Ts_Vld, Ts_Rdy, Ts_Data);
end procedure;
end;

View File

@@ -1,201 +0,0 @@
------------------------------------------------------------
-- Libraries
------------------------------------------------------------
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
use ieee.math_real.all;
library work;
use work.psi_common_math_pkg.all;
use work.psi_ms_daq_pkg.all;
library work;
use work.psi_tb_txt_util.all;
use work.psi_tb_compare_pkg.all;
------------------------------------------------------------
-- Package Header
------------------------------------------------------------
package psi_ms_daq_input_tb_pkg is
-- *** Generics Record ***
type Generics_t is record
StreamWidth_g : positive;
VldPulsed_g : boolean;
end record;
------------------------------------------------------------
-- Not exported Generics
------------------------------------------------------------
constant StreamBuffer_g : positive := 32;
constant StreamClkFreq_g : real := 125.0e6;
constant StreamTsFifoDepth_g : positive := 8;
constant StreamTimeout_g : real := 10.0e-6;
constant StreamUseTs_g : boolean := true;
-- Handwritten Stuff
constant FrameType_Trigger_c : string := "TRIGGER";
constant FrameType_Timeout_c : string := "TIMEOUT";
procedure ApplyStrData ( Samples : in integer;
TrigSpl : in integer := integer'high;
Timestamp : in integer;
Generics : in Generics_t;
signal Str_Clk : in std_logic;
signal Str_Vld : inout std_logic;
signal Str_Rdy : in std_logic;
signal Str_Data : inout std_logic_vector;
signal Str_Trig : inout std_logic;
signal Str_Ts : inout std_logic_vector;
DataOffs : in integer := 0);
procedure CheckAcqData ( Samples : in integer;
Timestamp : in integer;
Generics : in Generics_t;
FrameType : in string;
signal Clk : in std_logic;
signal Daq_Vld : in std_logic;
signal Daq_Rdy : inout std_logic;
signal Daq_Data : in Input2Daq_Data_t;
signal Ts_Vld : in std_logic;
signal Ts_Rdy : inout std_logic;
signal Ts_Data : in std_logic_vector;
IsBadTs : in boolean := false;
DataOffs : in integer := 0);
end package;
------------------------------------------------------------
-- Package Body
------------------------------------------------------------
package body psi_ms_daq_input_tb_pkg is
procedure ApplyStrData ( Samples : in integer;
TrigSpl : in integer := integer'high;
Timestamp : in integer;
Generics : in Generics_t;
signal Str_Clk : in std_logic;
signal Str_Vld : inout std_logic;
signal Str_Rdy : in std_logic;
signal Str_Data : inout std_logic_vector;
signal Str_Trig : inout std_logic;
signal Str_Ts : inout std_logic_vector;
DataOffs : in integer := 0) is
begin
Str_Trig <= '0';
Str_Ts <= std_logic_vector(to_unsigned(0, Str_Ts'length));
Str_Vld <= '1';
for SplCnt in 0 to Samples-1 loop
Str_Vld <= '1';
-- Apply Trigger
if SplCnt = TrigSpl then
Str_Trig <= '1';
Str_Ts <= std_logic_vector(to_unsigned(Timestamp, Str_Ts'length));
else
Str_Trig <= '0';
Str_Ts <= std_logic_vector(to_unsigned(0, Str_Ts'length));
end if;
-- Apply Data
Str_Data <= std_logic_vector(to_unsigned(SplCnt+DataOffs, Generics.StreamWidth_g));
wait until rising_edge(Str_Clk);
if Generics.VldPulsed_g then
Str_Trig <= '0';
Str_Vld <= '0';
Str_Data <= std_logic_vector(to_unsigned(0, Generics.StreamWidth_g));
wait until rising_edge(Str_Clk);
end if;
end loop;
Str_Vld <= '0';
Str_Trig <= '0';
Str_Ts <= std_logic_vector(to_unsigned(0, Str_Ts'length));
end procedure;
procedure CheckAcqData ( Samples : in integer;
Timestamp : in integer;
Generics : in Generics_t;
FrameType : in string;
signal Clk : in std_logic;
signal Daq_Vld : in std_logic;
signal Daq_Rdy : inout std_logic;
signal Daq_Data : in Input2Daq_Data_t;
signal Ts_Vld : in std_logic;
signal Ts_Rdy : inout std_logic;
signal Ts_Data : in std_logic_vector;
IsBadTs : in boolean := false;
DataOffs : in integer := 0) is
constant Qwords_c : integer := integer(ceil(real(Samples)*real(Generics.StreamWidth_g)/64.0));
constant SplPerQw_c : integer := 64/Generics.StreamWidth_g;
variable SplCnt_v : integer := 0;
variable SplData_v : std_logic_vector(Generics.StreamWidth_g-1 downto 0);
variable DelayedToTlast_v : boolean := false; -- It is possible that an empty word (0 bytes) with TLAST is sent at thed end of the frame in case of timeouts
constant Wraparound_c : integer := choose(Generics.StreamWidth_g < 32, 2**Generics.StreamWidth_g, integer'high);
begin
wait until rising_edge(Clk);
Daq_Rdy <= '1';
for qw in 0 to Qwords_c-1 loop
-- Wait for data
wait until rising_edge(Clk) and Daq_Vld = '1';
-- Check data
for spl in 0 to SplPerQw_c-1 loop
if SplCnt_v < Samples then
SplData_v := Daq_Data.Data((spl+1)*Generics.StreamWidth_g-1 downto spl*Generics.StreamWidth_g);
StdlvCompareInt((SplCnt_v+DataOffs) mod Wraparound_c, SplData_v, "received wrong data, sample" & IndexString(SplCnt_v), false);
SplCnt_v := SplCnt_v + 1;
end if;
end loop;
-- Check last, bytes
if qw = Qwords_c-1 then
-- If TLAST is not asserted, we can expect a delayed TLAST because of a timeout
if Daq_Data.Last = '0' then
DelayedToTlast_v := true;
end if;
StdlvCompareInt(Samples*Generics.StreamWidth_g/8-qw*8, Daq_Data.Bytes, "last bytes not correct", false);
else
StdlCompare(0, Daq_Data.Last, "last asserted unexpectedly, QWORD" & IndexString(qw));
StdlvCompareInt(8, Daq_Data.Bytes, "bytes not 8, QWORD" & IndexString(qw), false);
end if;
-- Check IsTrig
if FrameType = FrameType_Trigger_c and qw = Qwords_c-1 then
StdlCompare(1, Daq_Data.IsTrig, "IsTrig not asserted, QWORD" & IndexString(qw));
else
StdlCompare(0, Daq_Data.IsTrig, "IsTrig asserted unexpectedly, QWORD" & IndexString(qw));
end if;
-- Check IsTo
if FrameType = FrameType_Timeout_c and qw = Qwords_c-1 and not DelayedToTlast_v then
StdlCompare(1, Daq_Data.IsTo, "IsTo not asserted, QWORD" & IndexString(qw));
else
StdlCompare(0, Daq_Data.IsTo, "IsTo asserted unexpectedly, QWORD" & IndexString(qw));
end if;
end loop;
-- Check delayed TLAST
if DelayedToTlast_v then
wait until rising_edge(Clk) and Daq_Vld = '1';
if FrameType = FrameType_Timeout_c then
StdlCompare(1, Daq_Data.IsTo, "IsTo not asserted, QWORD" & IndexString(Qwords_c));
StdlvCompareInt(0, Daq_Data.Bytes, "delayed TLAST must have zero data bytes", false);
StdlCompare(0, Daq_Data.IsTrig, "delayed TLAST must be non-Trigger");
StdlCompare(1, Daq_Data.Last, "delayed TLAST must have LAST asserted");
else
report "###ERROR###: Delayed TLAST is only possible for timeout frames" severity error;
end if;
end if;
Daq_Rdy <= '0';
-- Check timestamp
if FrameType = FrameType_Trigger_c then
if not IsBadTs then
StdlCompare(1, Ts_Vld, "Ts_Vld not asserted");
end if;
StdlvCompareInt(Timestamp, Ts_Data, "Received wrong timestamp", true);
Ts_Rdy <= '1';
wait until rising_edge(Clk);
Ts_Rdy <= '0';
wait until rising_edge(Clk);
else
StdlCompare(0, Ts_Vld, "Ts_Vld asserted unexpectedly for timeout fram");
end if;
end procedure;
end;