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

Subversion Repositories qaz_libs

Compare Revisions

  • This comparison shows the changes necessary to convert path
    /qaz_libs/trunk/avalon_lib/syn
    from Rev 31 to Rev 33
    Reverse comparison

Rev 31 → Rev 33

/ast_monitor/altera_avalon_st_monitor_171/sim/altera_avalon_st_monitor.sv
0,0 → 1,292
// (C) 2001-2017 Intel Corporation. All rights reserved.
// Your use of Intel Corporation's design tools, logic functions and other
// software and tools, and its AMPP partner logic functions, and any output
// files from any of the foregoing (including device programming or simulation
// files), and any associated documentation or information are expressly subject
// to the terms and conditions of the Intel Program License Subscription
// Agreement, Intel FPGA IP License Agreement, or other applicable
// license agreement, including, without limitation, that your use is for the
// sole purpose of programming logic devices manufactured by Intel and sold by
// Intel or its authorized distributors. Please refer to the applicable
// agreement for further details.
 
 
// $Id: //acds/rel/17.1std/ip/sopc/components/verification/altera_avalon_st_monitor_bfm/altera_avalon_st_monitor.sv#1 $
// $Revision: #1 $
// $Date: 2017/07/30 $
//-----------------------------------------------------------------------------
// =head1 NAME
// altera_avalon_st_monitor
// =head1 SYNOPSIS
// Bridge with Avalon Bus Protocol Assertion Checker
//-----------------------------------------------------------------------------
// =head1 DESCRIPTION
// This module implements Avalon ST protocol assertion checking for simulation.
// The component acts as a simple repeater with Avalon bus signals
// passed through from the sink to source interface.
// The instantiated altera_avalon_st_monitor snoops all passing Avalon
// bus signals and performs assertion checking and measures coverage on
// Avalon Streaming protocol properties.
// Transactions in transit may also be captured in a transaction buffer and
// extracted from the monitor via the API.
// The macro ALTERA_AVALON_SIM_SVA is defined to disable SVA processing
// The macro ENABLE_ALTERA_AVALON_TRANSACTION_RECORDING must be defined to
// enable transaction monitoring
//-----------------------------------------------------------------------------
 
`timescale 1ps / 1ps
 
module altera_avalon_st_monitor(
clk,
reset,
 
sink_data,
sink_channel,
sink_valid,
sink_startofpacket,
sink_endofpacket,
sink_error,
sink_empty,
sink_ready,
src_data,
src_channel,
src_valid,
src_startofpacket,
src_endofpacket,
src_error,
src_empty,
src_ready
);
// =head1 PARAMETERS
parameter ST_SYMBOL_W = 8; // number of bits in one symbols
parameter ST_NUMSYMBOLS = 4; // number of symbols in one data
parameter ST_CHANNEL_W = 0; // width of channel signal
parameter ST_ERROR_W = 0; // width of error signal
parameter ST_EMPTY_W = 0; // width of empty signal, ST_EMPTY_W = log2(`ST_NUMSYMBOLS)
parameter ST_READY_LATENCY = 0; // fixed ready latency in cycles
parameter ST_MAX_CHANNELS = 1; // maximum number of channels
parameter USE_PACKET = 0; // data transfer in packet format
parameter USE_CHANNEL = 0; // use channel port
parameter USE_ERROR = 0; // use error port
parameter USE_READY = 1; // use ready port
parameter USE_VALID = 1; // use valid port
parameter USE_EMPTY = 0; // use empty port
parameter ST_BEATSPERCYCLE = 1; // Max number of packets per cycle
parameter ST_MAX_PACKET_SIZE = 1; // Max number of packet size covered
parameter VHDL_ID = 0; // VHDL BFM ID number
localparam ST_DATA_W = ST_SYMBOL_W * ST_NUMSYMBOLS;
localparam ST_MDATA_W = ST_BEATSPERCYCLE * ST_DATA_W;
localparam ST_MCHANNEL_W = ST_BEATSPERCYCLE * ST_CHANNEL_W;
localparam ST_MERROR_W = ST_BEATSPERCYCLE * ST_ERROR_W;
localparam ST_MEMPTY_W = ST_BEATSPERCYCLE * ST_EMPTY_W;
localparam TAP_W = ((ST_DATA_W == 0)? 1:ST_DATA_W) + // data
((ST_CHANNEL_W == 0)? 1:ST_CHANNEL_W) + // channel
1 + // valid
1 + // startofpacket
1 + // endofpacket
((ST_ERROR_W == 0)? 1:ST_ERROR_W) + // error
((ST_EMPTY_W == 0)? 1:ST_EMPTY_W) + // empty
1; // ready
localparam MTAP_W = ST_BEATSPERCYCLE*TAP_W;
// =head1 PINS
// =head2 Clock Interface
input clk;
input reset;
 
// =head2 Avalon Streaming Sink Interface
input [lindex(ST_MDATA_W) : 0] sink_data;
input [lindex(ST_MCHANNEL_W) : 0] sink_channel;
input [lindex(ST_BEATSPERCYCLE) : 0] sink_valid;
input [lindex(ST_BEATSPERCYCLE) : 0] sink_startofpacket;
input [lindex(ST_BEATSPERCYCLE) : 0] sink_endofpacket;
input [lindex(ST_MERROR_W) : 0] sink_error;
input [lindex(ST_MEMPTY_W) : 0] sink_empty;
output sink_ready;
 
// =head2 Avalon Streaming Source Interface
output [lindex(ST_MDATA_W) : 0] src_data;
output [lindex(ST_MCHANNEL_W) : 0] src_channel;
output [lindex(ST_BEATSPERCYCLE) : 0] src_valid;
output [lindex(ST_BEATSPERCYCLE) : 0] src_startofpacket;
output [lindex(ST_BEATSPERCYCLE) : 0] src_endofpacket;
output [lindex(ST_MERROR_W) : 0] src_error;
output [lindex(ST_MEMPTY_W) : 0] src_empty;
input src_ready;
 
// =cut
 
function int lindex;
// returns the left index for a vector having a declared width
// when width is 0, then the left index is set to 0 rather than -1
input [31:0] width;
lindex = (width > 0) ? (width-1) : 0;
endfunction
 
// outputs
logic sink_ready;
logic [lindex(ST_MDATA_W) : 0] src_data;
logic [lindex(ST_MCHANNEL_W) : 0] src_channel;
logic [lindex(ST_BEATSPERCYCLE) : 0] src_valid;
logic [lindex(ST_BEATSPERCYCLE) : 0] src_startofpacket;
logic [lindex(ST_BEATSPERCYCLE) : 0] src_endofpacket;
logic [lindex(ST_MERROR_W) : 0] src_error;
logic [lindex(ST_MEMPTY_W) : 0] src_empty;
logic [(MTAP_W)-ST_BEATSPERCYCLE : 0] tap;
always @(*) begin
sink_ready <= src_ready;
src_data <= sink_data;
src_channel <= sink_channel;
src_valid <= sink_valid;
src_startofpacket <= sink_startofpacket;
src_endofpacket <= sink_endofpacket;
src_error <= sink_error;
src_empty <= sink_empty;
 
tap <= {
sink_data,
sink_channel,
sink_valid,
sink_startofpacket,
sink_endofpacket,
sink_error,
sink_empty,
src_ready
};
end
//--------------------------------------------------------------------------
// =head1 ALTERA_AVALON_ST_MONITOR_ASSERTION
// This module implements Avalon-ST protocol simulation assertion checkers
// =cut
//--------------------------------------------------------------------------
altera_avalon_st_monitor_assertion
#(
.ST_SYMBOL_W (ST_SYMBOL_W),
.ST_NUMSYMBOLS (ST_NUMSYMBOLS),
.ST_CHANNEL_W (ST_CHANNEL_W),
.ST_ERROR_W (ST_ERROR_W),
.ST_EMPTY_W (ST_EMPTY_W),
 
.ST_READY_LATENCY(ST_READY_LATENCY),
.ST_MAX_CHANNELS (ST_MAX_CHANNELS),
.ST_BEATSPERCYCLE(ST_BEATSPERCYCLE),
 
.USE_PACKET (USE_PACKET),
.USE_CHANNEL (USE_CHANNEL),
.USE_ERROR (USE_ERROR),
.USE_READY (USE_READY),
.USE_VALID (USE_VALID),
.USE_EMPTY (USE_EMPTY)
)
monitor_assertion (
.clk (clk),
.reset (reset),
.tap (tap)
);
 
//--------------------------------------------------------------------------
// =head1 ALTERA_AVALON_ST_MONITOR_COVERAGE
// This module implements Avalon-ST protocol functional coverage measurements
// =cut
//--------------------------------------------------------------------------
altera_avalon_st_monitor_coverage
#(
.ST_SYMBOL_W (ST_SYMBOL_W),
.ST_NUMSYMBOLS (ST_NUMSYMBOLS),
.ST_CHANNEL_W (ST_CHANNEL_W),
.ST_ERROR_W (ST_ERROR_W),
.ST_EMPTY_W (ST_EMPTY_W),
.ST_BEATSPERCYCLE (ST_BEATSPERCYCLE),
.ST_READY_LATENCY (ST_READY_LATENCY),
.ST_MAX_CHANNELS (ST_MAX_CHANNELS),
 
.USE_PACKET (USE_PACKET),
.USE_CHANNEL (USE_CHANNEL),
.USE_ERROR (USE_ERROR),
.USE_READY (USE_READY),
.USE_VALID (USE_VALID),
.USE_EMPTY (USE_EMPTY),
.ST_MAX_PACKET_SIZE (ST_MAX_PACKET_SIZE)
)
monitor_coverage (
.clk (clk),
.reset (reset),
.tap (tap)
);
 
//--------------------------------------------------------------------------
// =head1 ALTERA_AVALON_ST_MONITOR_TRANSACTIONS
// This module implements Avalon-ST the transaction recorder.
// =cut
//--------------------------------------------------------------------------
 
`ifdef ENABLE_ALTERA_AVALON_TRANSACTION_RECORDING
altera_avalon_st_monitor_transactions
#(
.ST_SYMBOL_W (ST_SYMBOL_W),
.ST_NUMSYMBOLS (ST_NUMSYMBOLS),
.ST_CHANNEL_W (ST_CHANNEL_W),
.ST_ERROR_W (ST_ERROR_W),
.ST_EMPTY_W (ST_EMPTY_W),
.ST_BEATSPERCYCLE (ST_BEATSPERCYCLE),
.ST_READY_LATENCY (ST_READY_LATENCY),
.ST_MAX_CHANNELS (ST_MAX_CHANNELS),
 
.USE_PACKET (USE_PACKET),
.USE_CHANNEL (USE_CHANNEL),
.USE_ERROR (USE_ERROR),
.USE_READY (USE_READY),
.USE_VALID (USE_VALID),
.USE_EMPTY (USE_EMPTY),
.ST_MAX_PACKET_SIZE (ST_MAX_PACKET_SIZE)
)
monitor_trans (
.clk (clk),
.reset (reset),
.tap (tap)
);
`endif
// synthesis translate_off
import verbosity_pkg::*;
 
localparam VERSION = "17.1";
 
function automatic void hello();
// introduction message to the console
string message;
$sformat(message, "%m: - Hello from altera_avalon_st_monitor");
print(VERBOSITY_INFO, message);
`ifdef DISABLE_ALTERA_AVALON_SIM_SVA
$sformat(message, "%m: - Assertions disabled (DISABLE_ALTERA_AVALON_SIM_SVA defined)");
`else
$sformat(message, "%m: - Assertions enabled (DISABLE_ALTERA_AVALON_SIM_SVA undefined)");
`endif
print(VERBOSITY_INFO, message);
$sformat(message, "%m: - $Revision: #1 $");
print(VERBOSITY_INFO, message);
$sformat(message, "%m: - $Date: 2017/07/30 $");
print(VERBOSITY_INFO, message);
print_divider(VERBOSITY_INFO);
endfunction
 
initial begin
hello();
end
// synthesis translate_on
endmodule
/ast_monitor/altera_avalon_st_monitor_171/sim/altera_avalon_st_monitor_assertion.sv
0,0 → 1,550
// (C) 2001-2017 Intel Corporation. All rights reserved.
// Your use of Intel Corporation's design tools, logic functions and other
// software and tools, and its AMPP partner logic functions, and any output
// files from any of the foregoing (including device programming or simulation
// files), and any associated documentation or information are expressly subject
// to the terms and conditions of the Intel Program License Subscription
// Agreement, Intel FPGA IP License Agreement, or other applicable
// license agreement, including, without limitation, that your use is for the
// sole purpose of programming logic devices manufactured by Intel and sold by
// Intel or its authorized distributors. Please refer to the applicable
// agreement for further details.
 
 
// $File: //acds/main/ip/sopc/components/verification/altera_avalon_st_monitor_bfm/altera_avalon_st_monitor_tap.sv $
// $Revision: #7 $
// $Date: 2009/04/16 $
// $Author: pscheidt $
//-----------------------------------------------------------------------------
// =head1 NAME
// altera_avalon_st_monitor_assertion
// =head1 SYNOPSIS
// Streaming Avalon Bus Protocol Checker
//-----------------------------------------------------------------------------
// =head1 DESCRIPTION
// This module implements Avalon ST protocol assertion checking for simulation.
//-----------------------------------------------------------------------------
 
`timescale 1ns / 1ns
 
module altera_avalon_st_monitor_assertion(
clk,
reset,
tap
);
 
// =head1 PARAMETERS
parameter ST_SYMBOL_W = 8; // number of bits in one symbols
parameter ST_NUMSYMBOLS = 4; // number of symbols in one data
parameter ST_CHANNEL_W = 0; // width of channel signal
parameter ST_ERROR_W = 0; // width of error signal
parameter ST_EMPTY_W = 0; // width of empty signal, ST_EMPTY_W = log2(`ST_NUMSYMBOLS)
parameter ST_READY_LATENCY = 0; // fixed ready latency in cycles
parameter ST_MAX_CHANNELS = 1; // maximum number of channels
parameter USE_PACKET = 0; // data transfer in packet format
parameter USE_CHANNEL = 0; // use channel port
parameter USE_ERROR = 0; // use error port
parameter USE_READY = 1; // use ready port
parameter USE_VALID = 1; // use valid port
parameter USE_EMPTY = 0; // use empty port
parameter ST_BEATSPERCYCLE = 1; // Max number of packets per cycle
localparam ST_DATA_W = ST_SYMBOL_W * ST_NUMSYMBOLS;
localparam ST_MAX_EMPTY = 2**(ST_EMPTY_W) - 1;
localparam NUM_CHANNEL = ST_MAX_CHANNELS+1;
 
localparam TAP_W = ((ST_DATA_W == 0)? 1:ST_DATA_W) + // data
((ST_CHANNEL_W == 0)? 1:ST_CHANNEL_W) + // channel
1 + // valid
1 + // startofpacket
1 + // endofpacket
((ST_ERROR_W == 0)? 1:ST_ERROR_W) + // error
((ST_EMPTY_W == 0)? 1:ST_EMPTY_W) + // empty
1; // ready
// =head1 PINS
// =head2 Clock Interface
input clk;
input reset;
 
// =head2 Avalon Monitor Interface - will be defined as Streaming Sink
input [(TAP_W*ST_BEATSPERCYCLE)-ST_BEATSPERCYCLE:0] tap;
 
// =cut
 
function int lindex;
// returns the left index for a vector having a declared width
// when width is 0, then the left index is set to 0 rather than -1
input [31:0] width;
lindex = (width > 0) ? (width-1) : 0;
endfunction
 
//--------------------------------------------------------------------------
// synthesis translate_off
 
import verbosity_pkg::*;
typedef bit [lindex(ST_DATA_W) :0] STData_t;
typedef bit [lindex(ST_CHANNEL_W) :0] STChannel_t;
typedef bit [lindex(ST_EMPTY_W) :0] STEmpty_t;
typedef bit [lindex(ST_ERROR_W) :0] STError_t;
 
event signal_fatal_error;
 
event event_a_valid_legal;
event event_a_empty_legal;
event event_a_no_data_outside_packet;
event event_a_non_missing_endofpacket;
event event_a_non_missing_startofpacket;
event event_a_less_than_max_channel;
 
string fatal_message = "*unitialized*";
string message = "*unitialized*";
 
bit enable_a_valid_legal = 1;
bit enable_a_empty_legal = 1;
bit enable_a_no_data_outside_packet = 1;
bit enable_a_non_missing_endofpacket = 1;
bit enable_a_non_missing_startofpacket = 1;
bit enable_a_less_than_max_channel = 1;
 
//--------------------------------------------------------------------------
// unpack Avalon bus interface tap into individual port signals
logic ready;
logic [lindex(ST_BEATSPERCYCLE):0][lindex(ST_DATA_W):0] data;
logic [lindex(ST_BEATSPERCYCLE):0][lindex(ST_CHANNEL_W):0] channel;
logic [lindex(ST_BEATSPERCYCLE):0] valid;
logic [lindex(ST_BEATSPERCYCLE):0] startofpacket;
logic [lindex(ST_BEATSPERCYCLE):0] endofpacket;
logic [lindex(ST_BEATSPERCYCLE):0][lindex(ST_ERROR_W):0] error;
logic [lindex(ST_BEATSPERCYCLE):0][lindex(ST_EMPTY_W):0] empty;
 
always_comb begin
data <= tap[lindex(ST_DATA_W*ST_BEATSPERCYCLE)+lindex(ST_CHANNEL_W*ST_BEATSPERCYCLE)+
lindex(ST_ERROR_W*ST_BEATSPERCYCLE)+lindex(ST_EMPTY_W*ST_BEATSPERCYCLE)+3*ST_BEATSPERCYCLE+4:
lindex(ST_CHANNEL_W*ST_BEATSPERCYCLE)+lindex(ST_ERROR_W*ST_BEATSPERCYCLE)+lindex(ST_EMPTY_W*ST_BEATSPERCYCLE)+3*ST_BEATSPERCYCLE+4];
channel <= (USE_CHANNEL == 1)?
tap[lindex(ST_CHANNEL_W*ST_BEATSPERCYCLE)+lindex(ST_ERROR_W*ST_BEATSPERCYCLE)+
lindex(ST_EMPTY_W*ST_BEATSPERCYCLE)+3*ST_BEATSPERCYCLE+3:
lindex(ST_ERROR_W*ST_BEATSPERCYCLE)+lindex(ST_EMPTY_W*ST_BEATSPERCYCLE)+3*ST_BEATSPERCYCLE+3] : 0;
valid <= (USE_VALID == 1)?
tap[lindex(ST_ERROR_W*ST_BEATSPERCYCLE)+lindex(ST_EMPTY_W*ST_BEATSPERCYCLE)+3*ST_BEATSPERCYCLE+2:
lindex(ST_ERROR_W*ST_BEATSPERCYCLE)+lindex(ST_EMPTY_W*ST_BEATSPERCYCLE)+2*ST_BEATSPERCYCLE+3] : 1;
startofpacket <= (USE_PACKET == 1)?
tap[lindex(ST_ERROR_W*ST_BEATSPERCYCLE)+lindex(ST_EMPTY_W*ST_BEATSPERCYCLE)+2*ST_BEATSPERCYCLE+2:
lindex(ST_ERROR_W*ST_BEATSPERCYCLE)+lindex(ST_EMPTY_W*ST_BEATSPERCYCLE)+ST_BEATSPERCYCLE+3] : 0;
endofpacket <= (USE_PACKET == 1)?
tap[lindex(ST_ERROR_W*ST_BEATSPERCYCLE)+lindex(ST_EMPTY_W*ST_BEATSPERCYCLE)+ST_BEATSPERCYCLE+2:
lindex(ST_ERROR_W*ST_BEATSPERCYCLE)+lindex(ST_EMPTY_W*ST_BEATSPERCYCLE)+3] : 0;
error <= (USE_ERROR == 1)?
tap[lindex(ST_ERROR_W*ST_BEATSPERCYCLE)+lindex(ST_EMPTY_W*ST_BEATSPERCYCLE)+2:
lindex(ST_EMPTY_W*ST_BEATSPERCYCLE)+2] : 0;
empty <= (USE_EMPTY == 1)? tap[lindex(ST_EMPTY_W*ST_BEATSPERCYCLE)+1:1] : 0;
ready <= (USE_READY == 1)? tap[0:0] : 1;
end
 
//--------------------------------------------------------------------------
// General Statistics Counters
//--------------------------------------------------------------------------
 
logic [31:0] clock_counter;
logic [31:0] sop_counter;
logic [31:0] eop_counter;
 
logic sop_counter_reset = 0;
logic eop_counter_reset = 0;
logic [255:0] sop_channel_used = '0;
logic [255:0] eop_channel_used = '1;
logic [lindex(ST_BEATSPERCYCLE):0] sop_error_in_channel = '0;
logic [lindex(ST_BEATSPERCYCLE):0] eop_error_in_channel = '0;
logic [lindex(ST_BEATSPERCYCLE):0] data_outside_packet = '0;
 
always @(posedge clk) begin
if (reset)
clock_counter <= 0;
else
clock_counter <= clock_counter + 1;
end
 
always @(posedge clk) begin
if (reset) begin
sop_counter <= 0;
end else if (sop_counter_reset) begin
sop_counter_reset <= 0;
sop_counter <= 0;
end else begin
for (int i=0; i<ST_BEATSPERCYCLE; i++) begin
if ((USE_VALID && valid[i]) || !USE_VALID) begin
if ((ST_READY_LATENCY > 0) || (USE_READY && (ST_READY_LATENCY == 0) && ready) || !USE_READY) begin
sop_counter <= (USE_PACKET && valid[i] && startofpacket[i]) ? sop_counter + 1 : sop_counter;
end
end
end
end
end
 
always @(posedge clk) begin
if (reset) begin
eop_counter <= 0;
end else if (eop_counter_reset) begin
eop_counter_reset <= 0;
eop_counter <= 0;
end else begin
for (int i=0; i<ST_BEATSPERCYCLE; i++) begin
if ((USE_VALID && valid[i]) || !USE_VALID) begin
if ((ST_READY_LATENCY > 0) || (USE_READY && (ST_READY_LATENCY == 0) && ready) || !USE_READY) begin
eop_counter <= (USE_PACKET && valid[i] && endofpacket[i]) ? eop_counter + 1 : eop_counter;
end
end
end
end
end
 
//--------------------------------------------------------------------------
// Private Methods
//--------------------------------------------------------------------------
 
//--------------------------------------------------------------------------
// =head1 Public Methods API
// This section describes the public methods in the application programming
// interface (API). In this case the application program is the test bench
// which instantiates and controls and queries state of this component.
// Test programs must only use these public access methods and events to
// communicate with this BFM component. The API and the module pins
// are the only interfaces in this component that are guaranteed to be
// stable. The API will be maintained for the life of the product.
// While we cannot prevent a test program from directly accessing internal
// tasks, functions, or data private to the BFM, there is no guarantee that
// these will be present in the future. In fact, it is best for the user
// to assume that the underlying implementation of this component can
// and will change.
// =cut
//--------------------------------------------------------------------------
// Master Assertions API
function automatic void set_enable_a_valid_legal( // public
bit assert_enable
);
// enable or disable a_valid_legal assertion
enable_a_valid_legal = assert_enable;
endfunction
 
function automatic void set_enable_a_empty_legal( // public
bit assert_enable
);
// enable or disable a_empty_legal assertion
enable_a_empty_legal = assert_enable;
endfunction
 
function automatic void set_enable_a_no_data_outside_packet( // public
bit assert_enable
);
// enable or disable a_no_data_outside_packet assertion
enable_a_no_data_outside_packet = assert_enable;
endfunction
function automatic void set_enable_a_non_missing_endofpacket( // public
bit assert_enable
);
// enable or disable a_non_missing_endofpacket assertion
enable_a_non_missing_endofpacket = assert_enable;
endfunction
 
function automatic void set_enable_a_non_missing_startofpacket( // public
bit assert_enable
);
// enable or disable a_non_missing_startofpacket assertion
enable_a_non_missing_startofpacket = assert_enable;
endfunction
 
function automatic void set_enable_a_less_than_max_channel( // public
bit assert_enable
);
// enable or disable a_less_than_max_channel assertion
enable_a_less_than_max_channel = assert_enable;
endfunction
// =cut
function automatic logic [31:0] get_sop_counter();
return sop_counter;
if (USE_PACKET == 0) begin
$sformat(message, "%m: No packet signals in this stream (USE_PACKET=0).");
print(VERBOSITY_WARNING, message);
end
endfunction
 
function automatic void reset_sop_counter();
sop_counter_reset = 1'b1;
endfunction
function automatic logic [31:0] get_eop_counter();
return eop_counter;
if (USE_PACKET == 0) begin
$sformat(message, "%m: No packet signals in this stream (USE_PACKET=0).");
print(VERBOSITY_WARNING, message);
end
endfunction
 
function automatic void reset_eop_counter();
eop_counter_reset = 1'b1;
endfunction
 
// remaining API declarations will go here
//--------------------------------------------------------------------------
event fatal_error;
always @(fatal_error) begin
$sformat(message, "%m: Terminate simulation.");
print(VERBOSITY_FAILURE, message);
abort_simulation();
end
//--------------------------------------------------------------------------
// =head1 Assertion Checkers and Coverage Monitors
// The assertion checkers in this module are only executable on simulators
// supporting the SystemVerilog Assertion (SVA) language.
// Mentor Modelsim AE and SE do not support this.
// Simulators that are supported include: Synopsys VCS and Mentor questasim.
// The assertion checking logic in this module must be explicitly enabled
// so that designs using this module can still be compiled on Modelsim without
// changes. To disable assertions define the following macro in the testbench
// or on the command line with: +define+DISABLE_ALTERA_AVALON_SIM_SVA.
// =cut
//--------------------------------------------------------------------------
function automatic void print_assertion(
string message_in
);
string message_out;
$sformat(message_out, "ASSERTION: %s", message_in);
print(VERBOSITY_FAILURE, message_out);
endfunction
 
 
// Counter for general assertion counters
always @(posedge clk)
begin
for (int i=0; i<ST_BEATSPERCYCLE; i++) begin
if ((USE_VALID && valid[i]) || !USE_VALID) begin
if ((ST_READY_LATENCY > 0) || (USE_READY && (ST_READY_LATENCY == 0) && ready) || !USE_READY) begin
check_sop_eop_valid(i);
end
end else begin
data_outside_packet[i] = 0;
end
end
end
always @(posedge clk)
begin
if (reset) begin
sop_channel_used = '0;
eop_channel_used = '1;
sop_error_in_channel = '0;
eop_error_in_channel = '0;
data_outside_packet = '0;
end
end
task automatic check_sop_eop_valid(int current_beat);
if (startofpacket[current_beat]) begin
if (sop_channel_used[channel[current_beat]] == 1)
sop_error_in_channel[current_beat] = 1;
else begin
sop_channel_used[channel[current_beat]] = 1;
sop_error_in_channel[current_beat] = 0;
end
eop_channel_used[channel[current_beat]] = 0;
end
if (endofpacket[current_beat]) begin
if (eop_channel_used[channel[current_beat]] == 1)
eop_error_in_channel[current_beat] = 1;
else begin
eop_channel_used[channel[current_beat]] = 1;
eop_error_in_channel[current_beat] = 0;
end
sop_channel_used[channel[current_beat]] = 0;
end
if (!startofpacket[current_beat] && !endofpacket[current_beat]) begin
if (!sop_channel_used[channel[current_beat]]) begin
data_outside_packet[current_beat] = 1;
end else begin
data_outside_packet[current_beat] = 0;
end
end else begin
data_outside_packet[current_beat] = 0;
end
endtask
// SVA assertion code lives within the following section block
// which is disabled when the macro DISABLE_ALTERA_AVALON_SIM_SVA is defined
 
`ifdef DISABLE_ALTERA_AVALON_SIM_SVA
// SVA assertion code has been disabled
 
`else
//--------------------------------------------------------------------------
// ASSERTION CODE BEGIN
//--------------------------------------------------------------------------
//-------------------------------------------------------------------------------
// =head2 Avalon Streaming Assertions
// The following are the assertions code focus on Streaming Source and Sink
// component checking
//-------------------------------------------------------------------------------
//------------------------------------------------------------------------------------
// =head3 p_valid_legal
// This property check if valid is not deasserted ST_READY_LATENCY cycle after ready
// is deasserted.
//------------------------------------------------------------------------------------
property p_valid_legal(current_beat);
@(posedge clk && enable_a_valid_legal && USE_VALID && USE_READY && ST_READY_LATENCY > 0)
disable iff (reset)
!ready |-> ##ST_READY_LATENCY !valid[current_beat];
endproperty
 
genvar i;
for (i=0; i<ST_BEATSPERCYCLE; i++) begin: st_monitor_assertion_01
a_valid_legal: assert property(p_valid_legal(i))
else begin
-> event_a_valid_legal;
print_assertion("valid asserted after ready deasserted");
end
end
//------------------------------------------------------------------------------------
// =head3 p_empty_legal
// This property check if empty non zero while endofpacket is asserted or empty value
// larger or equal to ST_NUMSYMBOLS
//------------------------------------------------------------------------------------
property p_empty_legal(current_beat);
@(posedge clk && enable_a_empty_legal && USE_EMPTY && USE_PACKET)
disable iff (reset)
valid[current_beat] && (empty[current_beat] > 0) && (clock_counter > 0) &&
((USE_READY && (ST_READY_LATENCY == 0) && ready) ||
!USE_READY || (ST_READY_LATENCY > 0))
|-> endofpacket[current_beat] && (empty[current_beat] < ST_NUMSYMBOLS);
endproperty
 
for (i=0; i<ST_BEATSPERCYCLE; i++) begin: st_monitor_assertion_02
a_empty_legal: assert property(p_empty_legal(i))
else begin
-> event_a_empty_legal;
print_assertion("illegal empty value");
end
end
//------------------------------------------------------------------------------------
// =head3 p_no_data_outside_packet
// This property check if that valid is asserted outside the packet transfer
//------------------------------------------------------------------------------------
property p_no_data_outside_packet(current_beat);
@(posedge clk && enable_a_no_data_outside_packet && USE_VALID && USE_PACKET)
disable iff (reset)
valid[current_beat] && !startofpacket[current_beat] && !endofpacket[current_beat] &&
((USE_READY && (ST_READY_LATENCY == 0) && ready) ||
!USE_READY || (ST_READY_LATENCY > 0))
|-> ##1 !data_outside_packet[current_beat];
endproperty
 
for (i=0; i<ST_BEATSPERCYCLE; i++) begin: st_monitor_assertion_03
a_no_data_outside_packet: assert property(p_no_data_outside_packet(i))
else begin
-> event_a_no_data_outside_packet;
print_assertion("valid is asserted outside the packet transfer");
end
end
//------------------------------------------------------------------------------------
// =head3 p_non_missing_endofpacket
// This property check if consecutive startofpacket without endofpacket occurs
//------------------------------------------------------------------------------------
property p_non_missing_endofpacket(current_beat);
@(posedge clk && enable_a_non_missing_endofpacket && USE_PACKET)
disable iff (reset)
startofpacket[current_beat] && valid[current_beat] &&
((USE_READY && (ST_READY_LATENCY == 0) && ready) ||
!USE_READY || (ST_READY_LATENCY > 0))
|-> ##1 !sop_error_in_channel[current_beat];
endproperty
 
for (i=0; i<ST_BEATSPERCYCLE; i++) begin: st_monitor_assertion_04
a_non_missing_endofpacket: assert property(p_non_missing_endofpacket(i))
else begin
-> event_a_non_missing_endofpacket;
print_assertion("consecutive startofpacket without endofpacket");
end
end
//------------------------------------------------------------------------------------
// =head3 p_non_missing_startofpacket
// This property check if consecutive endofpacket without endofpacket occurs
//------------------------------------------------------------------------------------
property p_non_missing_startofpacket(current_beat);
@(posedge clk && enable_a_non_missing_startofpacket && USE_PACKET)
disable iff (reset)
endofpacket[current_beat] && valid[current_beat] && !startofpacket[current_beat] &&
((USE_READY && (ST_READY_LATENCY == 0) && ready) ||
!USE_READY || (ST_READY_LATENCY > 0))
|-> ##1 !eop_error_in_channel[current_beat];
endproperty
 
for (i=0; i<ST_BEATSPERCYCLE; i++) begin: st_monitor_assertion_05
a_non_missing_startofpacket: assert property(p_non_missing_startofpacket(i))
else begin
-> event_a_non_missing_startofpacket;
print_assertion("consecutive endofpacket without startofpacket");
end
end
//------------------------------------------------------------------------------------
// =head3 p_less_than_max_channel
// This property checks if channel size is less than ST_MAX_CHANNELS
//------------------------------------------------------------------------------------
property p_less_than_max_channel(current_beat);
@(posedge clk && enable_a_less_than_max_channel && USE_CHANNEL)
disable iff (reset)
valid[current_beat] && (channel[current_beat] > 0) && (clock_counter > 0) &&
((USE_READY && (ST_READY_LATENCY == 0) && ready) ||
!USE_READY || (ST_READY_LATENCY > 0))
|-> (channel[current_beat] <= ST_MAX_CHANNELS);
endproperty
 
for (i=0; i<ST_BEATSPERCYCLE; i++) begin: st_monitor_assertion_06
a_less_than_max_channel: assert property(p_less_than_max_channel(i))
else begin
-> event_a_less_than_max_channel;
print_assertion("channel size must be within ST_MAX_CHANNELS");
end
end
// =cut
//--------------------------------------------------------------------------
// ASSERTION CODE END
//--------------------------------------------------------------------------
`endif
 
// synthesis translate_on
 
endmodule
 
 
/ast_monitor/altera_avalon_st_monitor_171/sim/altera_avalon_st_monitor_coverage.sv
0,0 → 1,1651
// (C) 2001-2017 Intel Corporation. All rights reserved.
// Your use of Intel Corporation's design tools, logic functions and other
// software and tools, and its AMPP partner logic functions, and any output
// files from any of the foregoing (including device programming or simulation
// files), and any associated documentation or information are expressly subject
// to the terms and conditions of the Intel Program License Subscription
// Agreement, Intel FPGA IP License Agreement, or other applicable
// license agreement, including, without limitation, that your use is for the
// sole purpose of programming logic devices manufactured by Intel and sold by
// Intel or its authorized distributors. Please refer to the applicable
// agreement for further details.
 
 
// $File: //acds/main/ip/sopc/components/verification/altera_avalon_st_monitor_bfm/altera_avalon_st_monitor_coverage.sv $
// $Revision: #7 $
// $Date: 2009/04/16 $
// $Author: klong $
//-----------------------------------------------------------------------------
// =head1 NAME
// altera_avalon_st_monitor_coverage
// =head1 SYNOPSIS
// Streaming Avalon Bus Protocol Checker
//-----------------------------------------------------------------------------
// =head1 DESCRIPTION
// This module implements Avalon ST protocol coverage processing for simulation.
//-----------------------------------------------------------------------------
 
`timescale 1ns / 1ns
 
module altera_avalon_st_monitor_coverage(
clk,
reset,
tap
);
 
// =head1 PARAMETERS
parameter ST_SYMBOL_W = 8; // number of bits in one symbols
parameter ST_NUMSYMBOLS = 4; // number of symbols in one data
parameter ST_CHANNEL_W = 0; // width of channel signal
parameter ST_ERROR_W = 0; // width of error signal
parameter ST_EMPTY_W = 0; // width of empty signal
parameter ST_READY_LATENCY = 0; // fixed ready latency in cycles
parameter ST_MAX_CHANNELS = 1; // maximum number of channels
parameter USE_PACKET = 0; // data transfer in packet format
parameter USE_CHANNEL = 0; // use channel port
parameter USE_ERROR = 0; // use error port
parameter USE_READY = 1; // use ready port
parameter USE_VALID = 1; // use valid port
parameter USE_EMPTY = 0; // use empty port
parameter ST_BEATSPERCYCLE = 1; // Max number of packets per cycle
parameter ST_MAX_PACKET_SIZE = 1; // Max number of packet size covered
localparam ST_DATA_W = ST_SYMBOL_W * ST_NUMSYMBOLS;
localparam ST_MAX_EMPTY = 2**(ST_EMPTY_W) - 1;
localparam NUM_CHANNEL = ST_MAX_CHANNELS+1;
 
localparam TAP_W = ((ST_DATA_W == 0)? 1:ST_DATA_W) + // data
((ST_CHANNEL_W == 0)? 1:ST_CHANNEL_W) + // channel
1 + // valid
1 + // startofpacket
1 + // endofpacket
((ST_ERROR_W == 0)? 1:ST_ERROR_W) + // error
((ST_EMPTY_W == 0)? 1:ST_EMPTY_W) + // empty
1; // ready
// =head1 PINS
// =head2 Clock Interface
input clk;
input reset;
 
// =head2 Avalon Monitor Interface - will be defined as Streaming Sink
input [(TAP_W*ST_BEATSPERCYCLE)-ST_BEATSPERCYCLE:0] tap;
 
// =cut
function int lindex;
// returns the left index for a vector having a declared width
// when width is 0, then the left index is set to 0 rather than -1
input [31:0] width;
lindex = (width > 0) ? (width-1) : 0;
endfunction
 
function automatic int __floor1(
bit [31:0] arg
);
__floor1 = (arg <1) ? 1 : arg;
endfunction
 
//--------------------------------------------------------------------------
// synthesis translate_off
 
import verbosity_pkg::*;
typedef bit [lindex(ST_DATA_W) :0] STData_t;
typedef bit [lindex(ST_CHANNEL_W) :0] STChannel_t;
typedef bit [lindex(ST_EMPTY_W) :0] STEmpty_t;
typedef bit [lindex(ST_ERROR_W) :0] STError_t;
 
string message = "*unitialized*";
bit covergroup_settings_changed_flag = 0;
bit enable_c_packet_no_idles_no_back_pressure = 1;
bit enable_c_packet_with_idles = 1;
bit enable_c_packet_with_back_pressure = 1;
bit enable_c_channel_change_in_packet = 1;
bit enable_c_empty = 1;
bit enable_c_transfer = 1;
bit enable_c_error = 1;
bit enable_c_packet = 1;
bit enable_c_b2b_packet_different_channel = 1;
bit enable_c_b2b_packet_same_channel = 1;
bit enable_c_b2b_data_different_channel = 1;
bit enable_c_b2b_data_same_channel = 1;
bit enable_c_valid_non_ready = 1;
bit enable_c_non_valid_ready = 1;
bit enable_c_non_valid_non_ready = 1;
bit enable_c_transaction_after_reset = 1;
bit enable_c_packet_size = 1;
bit enable_c_multiple_packet_per_cycle = 1;
bit enable_c_single_packet_per_cycle = 1;
bit enable_c_idle_beat_between_packet = 1;
bit enable_c_all_idle_beats = 1;
bit enable_c_all_valid_beats = 1;
bit enable_c_partial_valid_beats = 1;
bit enable_c_b2b_packet_within_single_cycle = 1;
bit enable_c_b2b_packet_in_different_cycle = 1;
bit enable_c_error_in_middle_of_packet = 1;
//--------------------------------------------------------------------------
// unpack Avalon bus interface tap into individual port signals
logic ready;
logic [lindex(ST_BEATSPERCYCLE):0][lindex(ST_DATA_W):0] data;
logic [lindex(ST_BEATSPERCYCLE):0][lindex(ST_CHANNEL_W):0] channel;
logic [lindex(ST_BEATSPERCYCLE):0] valid;
logic [lindex(ST_BEATSPERCYCLE):0] startofpacket;
logic [lindex(ST_BEATSPERCYCLE):0] endofpacket;
logic [lindex(ST_BEATSPERCYCLE):0][lindex(ST_ERROR_W):0] error;
logic [lindex(ST_BEATSPERCYCLE):0][lindex(ST_EMPTY_W):0] empty;
 
always_comb begin
data <= tap[lindex(ST_DATA_W*ST_BEATSPERCYCLE)+lindex(ST_CHANNEL_W*ST_BEATSPERCYCLE)+
lindex(ST_ERROR_W*ST_BEATSPERCYCLE)+lindex(ST_EMPTY_W*ST_BEATSPERCYCLE)+3*ST_BEATSPERCYCLE+4:
lindex(ST_CHANNEL_W*ST_BEATSPERCYCLE)+lindex(ST_ERROR_W*ST_BEATSPERCYCLE)+lindex(ST_EMPTY_W*ST_BEATSPERCYCLE)+3*ST_BEATSPERCYCLE+4];
channel <= (USE_CHANNEL == 1)?
tap[lindex(ST_CHANNEL_W*ST_BEATSPERCYCLE)+lindex(ST_ERROR_W*ST_BEATSPERCYCLE)+
lindex(ST_EMPTY_W*ST_BEATSPERCYCLE)+3*ST_BEATSPERCYCLE+3:
lindex(ST_ERROR_W*ST_BEATSPERCYCLE)+lindex(ST_EMPTY_W*ST_BEATSPERCYCLE)+3*ST_BEATSPERCYCLE+3] : 0;
valid <= (USE_VALID == 1)?
tap[lindex(ST_ERROR_W*ST_BEATSPERCYCLE)+lindex(ST_EMPTY_W*ST_BEATSPERCYCLE)+3*ST_BEATSPERCYCLE+2:
lindex(ST_ERROR_W*ST_BEATSPERCYCLE)+lindex(ST_EMPTY_W*ST_BEATSPERCYCLE)+2*ST_BEATSPERCYCLE+3] :
(reset == 1)? 'x: 1;
startofpacket <= (USE_PACKET == 1)?
tap[lindex(ST_ERROR_W*ST_BEATSPERCYCLE)+lindex(ST_EMPTY_W*ST_BEATSPERCYCLE)+2*ST_BEATSPERCYCLE+2:
lindex(ST_ERROR_W*ST_BEATSPERCYCLE)+lindex(ST_EMPTY_W*ST_BEATSPERCYCLE)+ST_BEATSPERCYCLE+3] : 0;
endofpacket <= (USE_PACKET == 1)?
tap[lindex(ST_ERROR_W*ST_BEATSPERCYCLE)+lindex(ST_EMPTY_W*ST_BEATSPERCYCLE)+ST_BEATSPERCYCLE+2:
lindex(ST_ERROR_W*ST_BEATSPERCYCLE)+lindex(ST_EMPTY_W*ST_BEATSPERCYCLE)+3] : 0;
error <= (USE_ERROR == 1)?
tap[lindex(ST_ERROR_W*ST_BEATSPERCYCLE)+lindex(ST_EMPTY_W*ST_BEATSPERCYCLE)+2:
lindex(ST_EMPTY_W*ST_BEATSPERCYCLE)+2] : 0;
empty <= (USE_EMPTY == 1)? tap[lindex(ST_EMPTY_W*ST_BEATSPERCYCLE)+1:1] : 0;
ready <= (USE_READY == 1)? tap[0:0] : 1;
end
 
//--------------------------------------------------------------------------
// General Statistics Counters
//--------------------------------------------------------------------------
 
logic [31:0] clock_counter;
logic [31:0] sop_counter;
logic [31:0] eop_counter;
 
logic sop_counter_reset = 0;
logic eop_counter_reset = 0;
 
logic [lindex(NUM_CHANNEL):0] packet_no_idles_no_back_pressure_flag = '1;
logic [lindex(NUM_CHANNEL):0] packet_with_back_pressure_flag = 0;
logic [lindex(NUM_CHANNEL):0] channel_change_in_packet_flag = 0;
logic [lindex(NUM_CHANNEL):0] packet_with_idles_flag = 0;
logic [31:0] idles_between_b2b_packet_same_channel_counter = 0;
logic [31:0] idles_between_b2b_packet_different_channel_counter = 0;
logic [31:0] idles_between_b2b_data_same_channel_counter = 0;
logic [31:0] idles_between_b2b_data_different_channel_counter = 0;
logic [lindex(NUM_CHANNEL):0] current_packet = 0;
logic [lindex(ST_BEATSPERCYCLE):0][lindex(ST_CHANNEL_W):0] past_channel = 0;
logic [lindex(ST_BEATSPERCYCLE):0] past_endofpacket = 0;
logic idles_between_packet_same_channel_sampled = 0;
logic idles_between_packet_different_channel_sampled = 0;
logic non_valid_ready_sampled = 0;
logic non_valid_non_ready_sampled = 0;
logic [lindex(ST_BEATSPERCYCLE):0] current_beat = 0;
logic [lindex(ST_BEATSPERCYCLE):0] current_beat_2 = 0;
logic [31:0] error_bit_num = 0;
logic [31:0] changed_channel = 0;
logic transaction_after_reset = 0;
logic all_valid_beats_flag = 0;
logic all_invalid_beats_flag = 0;
logic partial_valid_beats_flag = 0;
logic [31:0] idles_between_b2b_packet_transaction_counter = 0;
logic [31:0] idles_between_packet_within_single_transaction_sampled = 0;
logic [31:0] packet_per_transaction = 0;
logic [lindex(NUM_CHANNEL):0][31:0] packet_size = 0;
logic [31:0] error_in_middle_of_packet = 0;
logic [31:0] idles_between_packet_in_different_transaction_sampled = 0;
logic [31:0] invalid_beat_between_packet = 0;
logic packet_per_transaction_flag = 0;
logic channel_change = 0;
logic reset_status = 0;
always @(posedge clk) begin
if (reset)
clock_counter <= 0;
else
clock_counter <= clock_counter + 1;
end
 
always @(posedge clk) begin
if (reset) begin
sop_counter <= 0;
end else if (sop_counter_reset) begin
sop_counter_reset <= 0;
sop_counter <= 0;
end else begin
sop_counter <= (USE_PACKET && valid && startofpacket) ?
sop_counter + 1 :
sop_counter;
end
end
 
always @(posedge clk) begin
if (reset) begin
eop_counter <= 0;
end else if (eop_counter_reset) begin
eop_counter_reset <= 0;
eop_counter <= 0;
end else begin
eop_counter <= (USE_PACKET && valid && endofpacket) ?
eop_counter + 1 : eop_counter;
end
end
 
//--------------------------------------------------------------------------
// =head1 Public Methods API
// This section describes the public methods in the application programming
// interface (API). In this case the application program is the test bench
// which instantiates and controls and queries state of this component.
// Test programs must only use these public access methods and events to
// communicate with this BFM component. The API and the module pins
// are the only interfaces in this component that are guaranteed to be
// stable. The API will be maintained for the life of the product.
// While we cannot prevent a test program from directly accessing internal
// tasks, functions, or data private to the BFM, there is no guarantee that
// these will be present in the future. In fact, it is best for the user
// to assume that the underlying implementation of this component can
// and will change.
// =cut
//--------------------------------------------------------------------------
 
// ST Coverage API
function automatic void set_enable_c_packet_no_idles_no_back_pressure( // public
bit cover_enable
);
// enable or disable c_packet_no_idles_no_back_pressure cover group
enable_c_packet_no_idles_no_back_pressure = cover_enable;
coverage_settings_check(covergroup_settings_changed_flag, "c_packet_no_idles_no_back_pressure");
endfunction
 
function automatic void set_enable_c_packet_with_idles( // public
bit cover_enable
);
// enable or disable c_packet_with_idles cover group
enable_c_packet_with_idles = cover_enable;
coverage_settings_check(covergroup_settings_changed_flag, "c_packet_with_idles");
endfunction
 
function automatic void set_enable_c_packet_with_back_pressure( // public
bit cover_enable
);
// enable or disable c_packet_with_back_pressure cover group
enable_c_packet_with_back_pressure = cover_enable;
coverage_settings_check(covergroup_settings_changed_flag, "c_packet_with_back_pressure");
endfunction
function automatic void set_enable_c_channel_change_in_packet( // public
bit cover_enable
);
// enable or disable c_channel_change_in_packet cover group
enable_c_channel_change_in_packet = cover_enable;
coverage_settings_check(covergroup_settings_changed_flag, "c_channel_change_in_packet");
endfunction
 
function automatic void set_enable_c_empty( // public
bit cover_enable
);
// enable or disable c_empty cover group
enable_c_empty = cover_enable;
coverage_settings_check(covergroup_settings_changed_flag, "c_empty");
endfunction
 
function automatic void set_enable_c_transfer( // public
bit cover_enable
);
// enable or disable c_transfer cover group
enable_c_transfer = cover_enable;
coverage_settings_check(covergroup_settings_changed_flag, "c_transfer");
endfunction
function automatic void set_enable_c_error( // public
bit cover_enable
);
// enable or disable c_error cover group
enable_c_error = cover_enable;
coverage_settings_check(covergroup_settings_changed_flag, "c_error");
endfunction
function automatic void set_enable_c_packet( // public
bit cover_enable
);
// enable or disable c_packet cover group
enable_c_packet = cover_enable;
coverage_settings_check(covergroup_settings_changed_flag, "c_packet");
endfunction
function automatic void set_enable_c_b2b_packet_different_channel( // public
bit cover_enable
);
// enable or disable c_b2b_packet_different_channel cover group
enable_c_b2b_packet_different_channel = cover_enable;
coverage_settings_check(covergroup_settings_changed_flag, "c_b2b_packet_different_channel");
endfunction
function automatic void set_enable_c_b2b_packet_same_channel( // public
bit cover_enable
);
// enable or disable c_b2b_packet_same_channel cover group
enable_c_b2b_packet_same_channel = cover_enable;
coverage_settings_check(covergroup_settings_changed_flag, "c_b2b_packet_same_channel");
endfunction
function automatic void set_enable_c_b2b_data_different_channel( // public
bit cover_enable
);
// enable or disable c_b2b_data_different_channel cover group
enable_c_b2b_data_different_channel = cover_enable;
coverage_settings_check(covergroup_settings_changed_flag, "c_b2b_data_different_channel");
endfunction
function automatic void set_enable_c_b2b_data_same_channel( // public
bit cover_enable
);
// enable or disable c_b2b_data_same_channel cover group
enable_c_b2b_data_same_channel = cover_enable;
coverage_settings_check(covergroup_settings_changed_flag, "c_b2b_data_same_channel");
endfunction
function automatic void set_enable_c_valid_non_ready( // public
bit cover_enable
);
// enable or disable c_valid_non_ready cover group
enable_c_valid_non_ready = cover_enable;
coverage_settings_check(covergroup_settings_changed_flag, "c_valid_non_ready");
endfunction
function automatic void set_enable_c_non_valid_ready( // public
bit cover_enable
);
// enable or disable c_non_valid_ready cover group
enable_c_non_valid_ready = cover_enable;
coverage_settings_check(covergroup_settings_changed_flag, "c_non_valid_ready");
endfunction
function automatic void set_enable_c_non_valid_non_ready( // public
bit cover_enable
);
// enable or disable c_non_valid_non_ready cover group
enable_c_non_valid_non_ready = cover_enable;
coverage_settings_check(covergroup_settings_changed_flag, "c_non_valid_non_ready");
endfunction
 
function automatic void set_enable_c_transaction_after_reset( // public
bit cover_enable
);
// enable or disable transaction_after_reset cover group
enable_c_transaction_after_reset = cover_enable;
coverage_settings_check(covergroup_settings_changed_flag, "c_transaction_after_reset");
endfunction
function automatic void set_enable_c_packet_size( // public
bit cover_enable
);
// enable or disable c_packet_size cover group
enable_c_packet_size = cover_enable;
coverage_settings_check(covergroup_settings_changed_flag, "c_packet_size");
endfunction
function automatic void set_enable_c_multiple_packet_per_cycle( // public
bit cover_enable
);
// enable or disable c_multiple_packet_per_cycle cover group
enable_c_multiple_packet_per_cycle = cover_enable;
coverage_settings_check(covergroup_settings_changed_flag, "c_multiple_packet_per_cycle");
endfunction
function automatic void set_enable_c_single_packet_per_cycle( // public
bit cover_enable
);
// enable or disable c_single_packet_per_cycle cover group
enable_c_single_packet_per_cycle = cover_enable;
coverage_settings_check(covergroup_settings_changed_flag, "c_single_packet_per_cycle");
endfunction
function automatic void set_enable_c_idle_beat_between_packet( // public
bit cover_enable
);
// enable or disable c_idle_beat_between_packet cover group
enable_c_idle_beat_between_packet = cover_enable;
coverage_settings_check(covergroup_settings_changed_flag, "c_idle_beat_between_packet");
endfunction
function automatic void set_enable_c_all_valid_beats( // public
bit cover_enable
);
// enable or disable c_all_valid_beats cover group
enable_c_all_valid_beats = cover_enable;
coverage_settings_check(covergroup_settings_changed_flag, "c_all_valid_beats");
endfunction
function automatic void set_enable_c_all_idle_beats( // public
bit cover_enable
);
// enable or disable c_all_idle_beats cover group
enable_c_all_idle_beats = cover_enable;
coverage_settings_check(covergroup_settings_changed_flag, "c_all_idle_beats");
endfunction
function automatic void set_enable_c_partial_valid_beats( // public
bit cover_enable
);
// enable or disable c_partial_valid_beats cover group
enable_c_partial_valid_beats = cover_enable;
coverage_settings_check(covergroup_settings_changed_flag, "c_partial_valid_beats");
endfunction
function automatic void set_enable_c_b2b_packet_within_single_cycle( // public
bit cover_enable
);
// enable or disable c_b2b_packet_within_single_cycle cover group
enable_c_b2b_packet_within_single_cycle = cover_enable;
coverage_settings_check(covergroup_settings_changed_flag, "c_b2b_packet_within_single_cycle");
endfunction
function automatic void set_enable_c_b2b_packet_in_different_transaction( // public
bit cover_enable
);
// enable or disable c_b2b_packet_in_different_transaction cover group
enable_c_b2b_packet_in_different_cycle = cover_enable;
coverage_settings_check(covergroup_settings_changed_flag, "c_b2b_packet_in_different_cycle");
endfunction
function automatic void set_enable_c_error_in_middle_of_packet( // public
bit cover_enable
);
// enable or disable c_error_in_middle_of_packet cover group
enable_c_error_in_middle_of_packet = cover_enable;
coverage_settings_check(covergroup_settings_changed_flag, "c_error_in_middle_of_packet");
endfunction
// =cut
function automatic logic [31:0] get_sop_counter();
return sop_counter;
if (USE_PACKET == 0) begin
$sformat(message, "%m: No packet signals in this stream (USE_PACKET = 0).");
print(VERBOSITY_WARNING, message);
end
endfunction
 
function automatic void reset_sop_counter();
sop_counter_reset = 1'b1;
endfunction
function automatic logic [31:0] get_eop_counter();
return eop_counter;
if (USE_PACKET == 0) begin
$sformat(message, "%m: No packet signals in this stream (USE_PACKET = 0).");
print(VERBOSITY_WARNING, message);
end
endfunction
 
function automatic void reset_eop_counter();
eop_counter_reset = 1'b1;
endfunction
function void coverage_settings_check(
bit cover_flag,
string cover_name
);
string message;
if (cover_flag) begin
$sformat(message, "%m: - Changing %s covergroup settings during run-time will not be reflected",
cover_name);
print(VERBOSITY_WARNING, message);
end
endfunction
`ifdef DISABLE_ALTERA_AVALON_SIM_SVA
// SVA coverage code is disabled when this macro is defined
`else
//--------------------------------------------------------------------------
// COVERAGE CODE BEGIN
//--------------------------------------------------------------------------
 
function automatic void print_assertion( //private
string message_in
);
string message_out;
$sformat(message_out, "ASSERTION: %s", message_in);
print(VERBOSITY_FAILURE, message_out);
endfunction
 
function logic [1023:0] pow( //private
input int power_value
);
// This method return the maximum supported value for the port width.
pow = (2**(power_value) - 1);
endfunction
function automatic logic [31:0] count_ones ( //private
input logic [1023:0] value
);
// This method return number of 1 bits
if (value == 0)
count_ones = 0;
else if (value == 'x) begin
count_ones = 'x;
end else begin
for( count_ones = 0; value!= 0; value = value >> 1 )
count_ones += value & 1'b1;
end
endfunction
function integer log2( //private
input int value
);
// Mathematic logarithm function with base as 2.
value = value-1;
for (log2=0; value>0; log2=log2+1)
begin
value = value>>1;
end
endfunction
 
task sample_non_valid_ready();
fork
begin
repeat(ST_READY_LATENCY) begin
@(posedge clk);
end
non_valid_ready_sampled = 1;
end
join_none
endtask
//--------------------------------------------------------------------------
// =head1 Assertion Checkers and Coverage Monitors
// The assertion checkers in this module are only executable on simulators
// supporting the SystemVerilog Assertion (SVA) language.
// Mentor Modelsim AE and SE do not support this.
// Simulators that are supported include: Synopsys VCS and Mentor questasim.
// The assertion checking logic in this module must be explicitly enabled
// so that designs using this module can still be compiled on Modelsim without
// changes. To disable assertions define the following macro in the testbench
// or on the command line with: +define+DISABLE_ALTERA_AVALON_SIM_SVA.
// =cut
//--------------------------------------------------------------------------
 
always @(posedge clk)
begin
if (!reset) begin
for (int i=0; i<ST_BEATSPERCYCLE; i++) begin
current_beat = i;
//counter for general coverage
if (((USE_VALID && valid[i]) || !USE_VALID)) begin
if ((ST_READY_LATENCY > 0) || (USE_READY && (ST_READY_LATENCY == 0) && ready) || !USE_READY) begin
 
if (enable_c_transaction_after_reset && USE_VALID) begin
c_transaction_after_reset.sample();
transaction_after_reset = 0;
end
if (enable_c_transfer && USE_VALID && USE_READY) begin
c_transfer.sample();
end
 
if (enable_c_empty && USE_EMPTY) begin
c_empty.sample();
end
if (enable_c_error && USE_ERROR) begin
for (int j = 0; j < ST_ERROR_W; j++) begin
if (error[current_beat][j] == 1) begin
error_bit_num = j;
c_error.sample();
end
end
end
 
if (startofpacket[i]) begin
if (!endofpacket[i]) begin
current_packet[channel[i]] = 1;
end else begin
packet_size[channel[i]]++;
end
if (error[i] > 0) begin
error_in_middle_of_packet = 1;
end else begin
error_in_middle_of_packet = 0;
end
if (enable_c_error_in_middle_of_packet && USE_ERROR && USE_PACKET) begin
c_error_in_middle_of_packet.sample();
error_in_middle_of_packet = 0;
end
packet_no_idles_no_back_pressure_flag[channel[i]] = 1;
//counter to determine time to sample signal
if (i == 0) begin
if (channel[i] != past_channel[ST_BEATSPERCYCLE-1]) begin
idles_between_packet_same_channel_sampled = 0;
if (past_endofpacket[ST_BEATSPERCYCLE-1] == 1) begin
idles_between_packet_different_channel_sampled = 1;
idles_between_packet_in_different_transaction_sampled = 1;
end else begin
idles_between_packet_different_channel_sampled = 0;
idles_between_packet_in_different_transaction_sampled = 0;
end
end else begin
idles_between_packet_different_channel_sampled = 0;
if (past_endofpacket[ST_BEATSPERCYCLE-1] == 1) begin
idles_between_packet_same_channel_sampled = 1;
idles_between_packet_in_different_transaction_sampled = 1;
end else begin
idles_between_packet_same_channel_sampled = 0;
idles_between_packet_in_different_transaction_sampled = 0;
end
end
idles_between_packet_within_single_transaction_sampled = 0;
end else begin
if (channel[i] != channel[i-1]) begin
idles_between_packet_same_channel_sampled = 0;
if (endofpacket[i-1] == 1) begin
idles_between_packet_different_channel_sampled = 1;
idles_between_packet_within_single_transaction_sampled = 1;
end else begin
idles_between_packet_different_channel_sampled = 0;
idles_between_packet_within_single_transaction_sampled = 0;
end
end else begin
idles_between_packet_different_channel_sampled = 0;
if (endofpacket[i-1] == 1) begin
idles_between_packet_same_channel_sampled = 1;
idles_between_packet_within_single_transaction_sampled = 1;
end else begin
idles_between_packet_same_channel_sampled = 0;
idles_between_packet_within_single_transaction_sampled = 0;
end
end
idles_between_packet_in_different_transaction_sampled = 0;
end
if (enable_c_b2b_packet_different_channel && USE_CHANNEL && USE_PACKET && USE_VALID && (ST_MAX_CHANNELS > 0)) begin
if (idles_between_packet_different_channel_sampled) begin
c_b2b_packet_different_channel.sample();
end
end
 
if (enable_c_b2b_packet_same_channel && USE_PACKET && USE_VALID) begin
if (idles_between_packet_same_channel_sampled) begin
c_b2b_packet_same_channel.sample();
end
end
if (enable_c_b2b_packet_within_single_cycle && USE_PACKET && USE_VALID && (ST_BEATSPERCYCLE > 1)) begin
if (idles_between_packet_within_single_transaction_sampled) begin
c_b2b_packet_within_single_cycle.sample();
end
end
if (enable_c_b2b_packet_in_different_cycle && USE_PACKET && USE_VALID && (ST_BEATSPERCYCLE > 1)) begin
if (idles_between_packet_in_different_transaction_sampled) begin
c_b2b_packet_in_different_cycle.sample();
end
end
 
if ((count_ones(current_packet) == 1) || ((count_ones(current_packet) == 0) &&(endofpacket[i]))) begin
if (enable_c_idle_beat_between_packet && USE_VALID && USE_PACKET && (ST_BEATSPERCYCLE > 1)) begin
c_idle_beat_between_packet.sample();
invalid_beat_between_packet = 0;
end
end
end
for (int j = 0; j <NUM_CHANNEL; j++) begin
if (current_packet[j] == 1) begin
packet_size[j]++;
end
end
if (endofpacket[i]) begin
 
invalid_beat_between_packet = 0;
current_packet[channel[i]] = 0;
if (enable_c_packet && USE_PACKET) begin
c_packet.sample();
end
 
if (enable_c_packet_no_idles_no_back_pressure && USE_READY && USE_VALID && USE_PACKET) begin
c_packet_no_idles_no_back_pressure.sample();
end
if (enable_c_packet_with_idles && USE_PACKET && USE_VALID) begin
c_packet_with_idles.sample();
packet_with_idles_flag[channel[i]] = 0;
end
if (enable_c_channel_change_in_packet && USE_CHANNEL && USE_PACKET && (ST_MAX_CHANNELS > 0)) begin
c_channel_change_in_packet.sample();
channel_change_in_packet_flag[channel[i]] = 0;
end
if (enable_c_packet_with_back_pressure && USE_READY && USE_PACKET) begin
c_packet_with_back_pressure.sample();
packet_with_back_pressure_flag[channel[i]] = 0;
end
if (enable_c_packet_size && USE_PACKET) begin
c_packet_size.sample();
packet_size[channel[i]] = 0;
end
end
if (i == 0) begin
if (channel[i] != past_channel[ST_BEATSPERCYCLE-1]) begin
if (((count_ones(current_packet) == 1) && !startofpacket[i]) ||
(count_ones(current_packet) > 1)) begin
if(current_packet[past_channel[ST_BEATSPERCYCLE-1]] == 1) begin
channel_change_in_packet_flag[past_channel[ST_BEATSPERCYCLE-1]] = 1;
end
end
end
end else begin
if (channel[i] != channel[i-1]) begin
if (((count_ones(current_packet) == 1) && !startofpacket[i]) ||
(count_ones(current_packet) > 1)) begin
if(current_packet[channel[i-1]] == 1) begin
channel_change_in_packet_flag[channel[i-1]] = 1;
end
end
end
end
end else begin
if (count_ones(current_packet) == 0) begin
invalid_beat_between_packet = 1;
end
end
end else if (USE_VALID && (valid[i] == 0)) begin
if (count_ones(current_packet) == 0) begin
invalid_beat_between_packet = 1;
end
end
 
//counter for idles transaction
if (!valid[i]) begin
for (int j = 0; j <NUM_CHANNEL; j++) begin
if (current_packet[j] == 1) begin
packet_with_idles_flag[j] = 1;
packet_no_idles_no_back_pressure_flag[j] = 0;
end
end
end
// counter for back-pressure transaction
if (USE_READY && !ready) begin
for (int j = 0; j <NUM_CHANNEL; j++) begin
if (current_packet[j] == 1) begin
packet_no_idles_no_back_pressure_flag[j] = 0;
packet_with_back_pressure_flag[j] = 1;
end
end
end
//counter for b2b transfer
if ((USE_VALID && !valid[i]) || ((USE_READY && (ST_READY_LATENCY == 0) && !ready))) begin
if (current_packet[channel[i]] == 0) begin
idles_between_b2b_packet_same_channel_counter++;
end
idles_between_b2b_packet_different_channel_counter++;
idles_between_b2b_packet_transaction_counter++;
for (int j = 0; j <NUM_CHANNEL; j++) begin
if (current_packet[j] == 1) begin
packet_size[j]++;
end
end
end
if (i == 0) begin
if ((USE_VALID && !valid[i]) || (past_channel[ST_BEATSPERCYCLE-1] != channel[i]) ||
((USE_READY && (ST_READY_LATENCY == 0) && !ready))) begin
idles_between_b2b_data_same_channel_counter++;
end
if ((USE_VALID && !valid[i]) || (past_channel[ST_BEATSPERCYCLE-1] == channel[i]) ||
((USE_READY && (ST_READY_LATENCY == 0) && !ready))) begin
idles_between_b2b_data_different_channel_counter++;
end
end else begin
if ((USE_VALID && !valid[i]) || (channel[i-1] != channel[i]) || ((USE_READY && (ST_READY_LATENCY == 0) && !ready))) begin
idles_between_b2b_data_same_channel_counter++;
end
if ((USE_VALID && !valid[i]) || (channel[i-1] == channel[i]) || ((USE_READY && (ST_READY_LATENCY == 0) && !ready))) begin
idles_between_b2b_data_different_channel_counter++;
end
end
if (((USE_VALID && valid[i]) || !USE_VALID)) begin
if ((ST_READY_LATENCY > 0) || (USE_READY && (ST_READY_LATENCY == 0) && ready) || !USE_READY) begin
if (endofpacket[i]) begin
idles_between_b2b_packet_same_channel_counter = 0;
idles_between_b2b_packet_different_channel_counter = 0;
idles_between_b2b_packet_transaction_counter = 0;
end
end
if ((!startofpacket[i] && !endofpacket[i]) || (USE_READY && (ST_READY_LATENCY == 0) && !ready)) begin
idles_between_b2b_packet_different_channel_counter++;
idles_between_b2b_packet_transaction_counter++;
end
end
if (((USE_VALID && valid[i]) || !USE_VALID)) begin
if ((ST_READY_LATENCY > 0) || (USE_READY && (ST_READY_LATENCY == 0) && ready) || !USE_READY) begin
if (enable_c_b2b_data_different_channel && USE_CHANNEL && USE_VALID && (ST_MAX_CHANNELS > 0)) begin
c_b2b_data_different_channel.sample();
idles_between_b2b_data_different_channel_counter = 0;
end
if (enable_c_b2b_data_same_channel && USE_VALID) begin
c_b2b_data_same_channel.sample();
idles_between_b2b_data_same_channel_counter = 0;
end
end
end
 
if (!reset_status)
transaction_after_reset = 0;
end
// counter to capture previous cycle signal value
for (int i=0; i<ST_BEATSPERCYCLE; i++) begin
if((USE_VALID && valid[i]) || !USE_VALID) begin
if ((ST_READY_LATENCY > 0) || (USE_READY && (ST_READY_LATENCY == 0) && ready) || !USE_READY) begin
past_endofpacket[i] <= endofpacket[i];
for (int k = i; k < ST_BEATSPERCYCLE; k++) begin
past_channel[k] <= channel[k];
end
end else
past_endofpacket[i] <= 0;
end else begin
past_endofpacket[i] <= 0;
end
end
reset_status = 0;
end
end
always @(posedge clk)
begin
if (!reset) begin
if (ready) begin
if (ST_READY_LATENCY == 0) begin
non_valid_ready_sampled = 1;
end else begin
sample_non_valid_ready();
end
end
 
if (enable_c_valid_non_ready && USE_READY && USE_VALID && (ST_READY_LATENCY == 0)) begin
for (int i=0; i<ST_BEATSPERCYCLE; i++) begin
if (valid[i]) begin
c_valid_non_ready.sample();
end
end
end
if (enable_c_non_valid_ready && USE_READY && USE_VALID) begin
for (int i=0; i<ST_BEATSPERCYCLE; i++) begin
current_beat_2 = i;
if (non_valid_ready_sampled) begin
c_non_valid_ready.sample();
end
end
non_valid_ready_sampled = 0;
end
if (enable_c_non_valid_non_ready && USE_READY && USE_VALID) begin
for (int i=0; i<ST_BEATSPERCYCLE; i++) begin
if (!valid[i] && non_valid_non_ready_sampled) begin
c_non_valid_non_ready.sample();
end
end
end
if (USE_VALID && (ST_BEATSPERCYCLE > 1)) begin
if ((ST_READY_LATENCY > 0) || (USE_READY && (ST_READY_LATENCY == 0) && ready) || !USE_READY) begin
if (count_ones(valid) == ST_BEATSPERCYCLE) begin
all_valid_beats_flag = 1;
end else begin
all_valid_beats_flag = 0;
end
if ((count_ones(valid) == 0) && (valid[0] == 0)) begin
all_invalid_beats_flag = 1;
end else begin
all_invalid_beats_flag = 0;
end
if ((count_ones(valid) > 0) && (count_ones(valid) < ST_BEATSPERCYCLE)) begin
partial_valid_beats_flag = 1;
end else begin
partial_valid_beats_flag = 0;
end
if (enable_c_all_valid_beats && USE_VALID && (ST_BEATSPERCYCLE > 1)) begin
c_all_valid_beats.sample();
end
if (enable_c_all_idle_beats && USE_VALID && (ST_BEATSPERCYCLE > 1)) begin
c_all_idle_beats.sample();
end
if (enable_c_partial_valid_beats && USE_VALID && (ST_BEATSPERCYCLE > 1)) begin
c_partial_valid_beats.sample();
end
end
end
if (USE_PACKET && (ST_BEATSPERCYCLE > 1)) begin
for (int i=0; i<ST_BEATSPERCYCLE; i++) begin
if ((ST_READY_LATENCY > 0) || (USE_READY && (ST_READY_LATENCY == 0) && ready) || !USE_READY) begin
if (((USE_VALID && valid[i]) || !USE_VALID)) begin
if (i > 0) begin
for (int j = 0; j < i; j++) begin
if (valid[j] == 1) begin
packet_per_transaction_flag = 1;
end
if ((channel[i] != channel[j]) && valid[j]) begin
channel_change = 1;
end
end
if (channel_change && packet_per_transaction_flag) begin
packet_per_transaction++;
end else begin
if ((startofpacket[i]) && packet_per_transaction_flag) begin
packet_per_transaction++;
end
end
channel_change = 0;
end
end
 
if (i == (ST_BEATSPERCYCLE-1)) begin
if (enable_c_multiple_packet_per_cycle && USE_PACKET && (ST_BEATSPERCYCLE > 1)) begin
c_multiple_packet_per_cycle.sample();
end
if (enable_c_single_packet_per_cycle && USE_PACKET && (ST_BEATSPERCYCLE > 1)) begin
if ((valid > 0)) begin
c_single_packet_per_cycle.sample();
end
end
packet_per_transaction = 0;
end
end
end
packet_per_transaction_flag = 0;
end
end
end
always @(negedge reset)
begin
non_valid_non_ready_sampled = 1;
end
//counter while reset
always @(posedge clk)
begin
if (reset) begin
non_valid_ready_sampled = 0;
non_valid_non_ready_sampled = 0;
packet_no_idles_no_back_pressure_flag = '1;
packet_with_back_pressure_flag = 0;
idles_between_b2b_packet_same_channel_counter = 0;
idles_between_b2b_packet_different_channel_counter = 0;
channel_change_in_packet_flag = 0;
packet_with_idles_flag = 0;
idles_between_packet_same_channel_sampled = 0;
idles_between_packet_different_channel_sampled = 0;
current_packet = 0;
idles_between_b2b_data_same_channel_counter = 0;
idles_between_b2b_data_different_channel_counter = 0;
past_channel = 0;
past_endofpacket = 0;
transaction_after_reset = 1;
current_beat = 0;
current_beat_2 = 0;
changed_channel = 0;
all_valid_beats_flag = 0;
all_invalid_beats_flag = 0;
partial_valid_beats_flag = 0;
idles_between_b2b_packet_transaction_counter = 0;
idles_between_packet_within_single_transaction_sampled = 0;
packet_per_transaction = 0;
packet_size = 0;
error_in_middle_of_packet = 0;
idles_between_packet_in_different_transaction_sampled = 0;
invalid_beat_between_packet = 0;
packet_per_transaction_flag = 0;
reset_status = 1;
channel_change = 0;
end
end
// Flag for initial coverage settings
initial begin
#1 covergroup_settings_changed_flag = 1;
end
 
//-------------------------------------------------------------------------------
// =head2 Streaming Coverages
// The following are the cover group code focus on ST Monitor component coverage
//-------------------------------------------------------------------------------
//-------------------------------------------------------------------------------
// =head3 c_empty
// This cover group covers the different empty value
//-------------------------------------------------------------------------------
 
covergroup cg_empty;
cp_empty: coverpoint empty[current_beat]
{
bins cg_empty_cp_empty [] = {[0:ST_MAX_EMPTY]};
}
option.per_instance = 1;
endgroup
 
cg_empty c_empty;
 
initial begin
#1 if (enable_c_empty && USE_EMPTY) begin
c_empty = new();
end
end
 
//-------------------------------------------------------------------------------
// =head3 c_error
// This cover group covers the different error value
//-------------------------------------------------------------------------------
 
covergroup cg_error;
cp_error: coverpoint error_bit_num
{
bins cg_error_cp_error [] = {[0:lindex(ST_ERROR_W)]};
}
option.per_instance = 1;
endgroup
 
cg_error c_error;
 
initial begin
#1 if (enable_c_error && USE_ERROR) begin
c_error = new();
end
end
 
//-------------------------------------------------------------------------------
// =head3 c_transfer
// This cover group covers valid is asserted for different channel.
//-------------------------------------------------------------------------------
 
covergroup cg_transfer;
cp_transfer: coverpoint (channel[current_beat])
{
bins cg_transfer_cp_transfer [] = {[0:(USE_CHANNEL == 0? 0:lindex(NUM_CHANNEL))]};
}
option.per_instance = 1;
endgroup
 
cg_transfer c_transfer;
 
initial begin
#1 if (enable_c_transfer && USE_VALID && USE_READY) begin
c_transfer = new();
end
end
 
//-------------------------------------------------------------------------------
// =head3 c_packet
// This cover group covers packet transfer for different channel.
//-------------------------------------------------------------------------------
 
covergroup cg_packet;
cp_packet: coverpoint (channel[current_beat])
{
bins cg_packet_cp_packet [] = {[0:(USE_CHANNEL == 0? 0:lindex(NUM_CHANNEL))]};
}
option.per_instance = 1;
endgroup
 
cg_packet c_packet;
 
initial begin
#1 if (enable_c_packet && USE_PACKET) begin
c_packet = new();
end
end
//-------------------------------------------------------------------------------
// =head3 c_valid_non_ready
// This cover group covers valid is asserted while ready is deasserted.
//-------------------------------------------------------------------------------
 
covergroup cg_valid_non_ready;
cp_valid_non_ready: coverpoint ready
{
bins cg_valid_non_ready_cp_valid_non_ready = {0};
}
option.per_instance = 1;
endgroup
 
cg_valid_non_ready c_valid_non_ready;
 
initial begin
#1 if (enable_c_valid_non_ready && USE_READY
&& USE_VALID && (ST_READY_LATENCY == 0)) begin
c_valid_non_ready = new();
end
end
 
//-------------------------------------------------------------------------------
// =head3 c_non_valid_ready
// This cover group covers valid is deasserted at the N+ST_READ_LATENCY
// clock cycle if ready is asserted at N clock cycle.
//-------------------------------------------------------------------------------
 
covergroup cg_non_valid_ready;
cp_non_valid_ready: coverpoint valid[current_beat_2]
{
bins cg_non_valid_ready_cp_non_valid_ready = {0};
}
option.per_instance = 1;
endgroup
 
cg_non_valid_ready c_non_valid_ready;
 
initial begin
#1 if (enable_c_non_valid_ready && USE_READY && USE_VALID) begin
c_non_valid_ready = new();
end
end
 
//-------------------------------------------------------------------------------
// =head3 c_non_valid_non_ready
// This cover group covers idle cycle.
//-------------------------------------------------------------------------------
 
covergroup cg_non_valid_non_ready;
cp_non_valid_non_ready: coverpoint ready
{
bins cg_non_valid_non_ready_cp_non_valid_non_ready = {0};
}
option.per_instance = 1;
endgroup
 
cg_non_valid_non_ready c_non_valid_non_ready;
 
initial begin
#1 if (enable_c_non_valid_non_ready && USE_READY && USE_VALID) begin
c_non_valid_non_ready = new();
end
end
 
//-------------------------------------------------------------------------------
// =head3 c_packet_no_idles_no_back_pressure
// This cover group covers packet transaction without back pressure and idle
// cycles.
//-------------------------------------------------------------------------------
 
covergroup cg_packet_no_idles_no_back_pressure;
cp_packet_no_idles_no_back_pressure: coverpoint packet_no_idles_no_back_pressure_flag[channel[current_beat]]
{
bins cg_packet_no_idles_no_back_pressure_cp_packet_no_idles_no_back_pressure = {1};
}
option.per_instance = 1;
endgroup
 
cg_packet_no_idles_no_back_pressure c_packet_no_idles_no_back_pressure;
 
initial begin
#1 if (enable_c_packet_no_idles_no_back_pressure && USE_READY && USE_VALID && USE_PACKET) begin
c_packet_no_idles_no_back_pressure = new();
end
end
 
//-------------------------------------------------------------------------------
// =head3 c_packet_with_back_pressure
// This cover group covers packet transaction being back pressured.
//-------------------------------------------------------------------------------
 
covergroup cg_packet_with_back_pressure;
cp_packet_with_back_pressure: coverpoint packet_with_back_pressure_flag[channel[current_beat]]
{
bins cg_packet_with_back_pressure_cp_packet_with_back_pressure = {1};
}
option.per_instance = 1;
endgroup
 
cg_packet_with_back_pressure c_packet_with_back_pressure;
initial begin
#1 if (enable_c_packet_with_back_pressure && USE_READY && USE_PACKET) begin
c_packet_with_back_pressure = new();
end
end
 
//-------------------------------------------------------------------------------
// =head3 c_packet_with_idles
// This cover group covers covers packet transaction with idle cycles
//-------------------------------------------------------------------------------
 
covergroup cg_packet_with_idles;
cp_packet_with_idles: coverpoint packet_with_idles_flag[channel[current_beat]]
{
bins cg_packet_with_idles_cp_packet_with_idles = {1};
}
option.per_instance = 1;
endgroup
 
cg_packet_with_idles c_packet_with_idles;
 
initial begin
#1 if (enable_c_packet_with_idles && USE_PACKET && USE_VALID) begin
c_packet_with_idles = new();
end
end
 
//-------------------------------------------------------------------------------
// =head3 c_channel_change_in_packet
// This cover group covers changing channel within a packet transaction.
//-------------------------------------------------------------------------------
 
covergroup cg_channel_change_in_packet;
cp_channel_change_in_packet: coverpoint channel_change_in_packet_flag[channel[current_beat]]
{
bins cg_channel_change_in_packet_cp_channel_change_in_packet = {1};
}
option.per_instance = 1;
endgroup
 
cg_channel_change_in_packet c_channel_change_in_packet;
 
initial begin
#1 if (enable_c_channel_change_in_packet && USE_CHANNEL && USE_PACKET && (ST_MAX_CHANNELS > 0)) begin
c_channel_change_in_packet = new();
end
end
 
//-------------------------------------------------------------------------------
// =head3 c_b2b_packet_different_channel
// This cover group covers back to back packet transfer for different channel.
//-------------------------------------------------------------------------------
 
covergroup cg_b2b_packet_different_channel;
cp_b2b_packet_different_channel: coverpoint idles_between_b2b_packet_different_channel_counter
{
bins cg_b2b_packet_different_channel_cp_b2b_packet_different_channel = {0};
}
option.per_instance = 1;
endgroup
 
cg_b2b_packet_different_channel c_b2b_packet_different_channel;
 
initial begin
#1 if (enable_c_b2b_packet_different_channel && USE_CHANNEL && USE_PACKET && USE_VALID && (ST_MAX_CHANNELS > 0)) begin
c_b2b_packet_different_channel = new();
end
end
 
//-------------------------------------------------------------------------------
// =head3 c_b2b_packet_same_channel
// This cover group covers back to back packet transfer for same channel.
//-------------------------------------------------------------------------------
 
covergroup cg_b2b_packet_same_channel;
cp_b2b_packet_same_channel: coverpoint idles_between_b2b_packet_same_channel_counter
{
bins cg_b2b_packet_same_channel_cp_b2b_packet_same_channel = {0};
}
option.per_instance = 1;
endgroup
 
cg_b2b_packet_same_channel c_b2b_packet_same_channel;
 
initial begin
#1 if (enable_c_b2b_packet_same_channel && USE_PACKET && USE_VALID) begin
c_b2b_packet_same_channel = new();
end
end
 
//-------------------------------------------------------------------------------
// =head3 c_b2b_data_different_channel
// This cover group covers back to back data transfer for different channel.
//-------------------------------------------------------------------------------
 
covergroup cg_b2b_data_different_channel;
cp_b2b_data_different_channel: coverpoint idles_between_b2b_data_different_channel_counter
{
bins cg_b2b_data_different_channel_cp_b2b_data_different_channel = {0};
}
option.per_instance = 1;
endgroup
 
cg_b2b_data_different_channel c_b2b_data_different_channel;
 
initial begin
#1 if (enable_c_b2b_data_different_channel && USE_CHANNEL && USE_VALID && (ST_MAX_CHANNELS > 0)) begin
c_b2b_data_different_channel = new();
end
end
 
//-------------------------------------------------------------------------------
// =head3 c_b2b_data_same_channel
// This cover group covers back to back data transfer for same channel.
//-------------------------------------------------------------------------------
 
covergroup cg_b2b_data_same_channel;
cp_b2b_data_same_channel: coverpoint idles_between_b2b_data_same_channel_counter
{
bins cg_b2b_data_same_channel_cp_b2b_data_same_channel = {0};
}
option.per_instance = 1;
endgroup
 
cg_b2b_data_same_channel c_b2b_data_same_channel;
 
initial begin
#1 if (enable_c_b2b_data_same_channel && USE_VALID) begin
c_b2b_data_same_channel = new();
end
end
//-------------------------------------------------------------------------------
// =head3 c_transaction_after_reset
// This cover group covers first transaction after reset.
//-------------------------------------------------------------------------------
 
covergroup cg_transaction_after_reset;
cp_transaction_after_reset: coverpoint transaction_after_reset
{
bins cg_transaction_after_reset_cp_transaction_after_reset = {1};
}
option.per_instance = 1;
endgroup
 
cg_transaction_after_reset c_transaction_after_reset;
 
initial begin
#1 if (enable_c_transaction_after_reset && USE_VALID) begin
c_transaction_after_reset = new();
end
end
//-------------------------------------------------------------------------------
// =head3 c_packet_size
// This covers different size of packet from one until parameter
// ST_MAX_PACKET_SIZE. For the transaction larger than ST_MAX_PACKET_SIZE will
// count into another bin.
//-------------------------------------------------------------------------------
 
covergroup cg_packet_size;
cp_packet_size: coverpoint packet_size[channel[current_beat]]
{
bins cg_packet_size_cp_packet_size [] = {[1:(ST_MAX_PACKET_SIZE < 1)? 1:ST_MAX_PACKET_SIZE]};
bins cg_packet_size_cp_packet_size_high = {[(ST_MAX_PACKET_SIZE < 1)? 2:ST_MAX_PACKET_SIZE+1:$]};
}
option.per_instance = 1;
endgroup
 
cg_packet_size c_packet_size;
 
initial begin
#1 if (enable_c_packet_size && USE_PACKET) begin
c_packet_size = new();
end
end
 
//-------------------------------------------------------------------------------
// =head3 c_multiple_packet_per_cycle
// This cover group covers number of transactions that carry multiple packets
// per single cycle.
//-------------------------------------------------------------------------------
 
covergroup cg_multiple_packet_per_cycle;
cp_multiple_packet_per_cycle: coverpoint packet_per_transaction
{
bins cg_multiple_packet_per_cycle_cp_multiple_packet_per_cycle = {[1:(ST_BEATSPERCYCLE > 1)?ST_BEATSPERCYCLE:1]};
}
option.per_instance = 1;
endgroup
 
cg_multiple_packet_per_cycle c_multiple_packet_per_cycle;
 
initial begin
#1 if (enable_c_multiple_packet_per_cycle && USE_PACKET && ST_BEATSPERCYCLE > 1) begin
c_multiple_packet_per_cycle = new();
end
end
//-------------------------------------------------------------------------------
// =head3 c_single_packet_per_cycle
// This cover group covers number of transactions that carry one packet
// per single cycle.
//-------------------------------------------------------------------------------
 
covergroup cg_single_packet_per_cycle;
cp_single_packet_per_cycle: coverpoint packet_per_transaction
{
bins cg_single_packet_per_cycle_cp_single_packet_per_cycle = {0};
}
option.per_instance = 1;
endgroup
 
cg_single_packet_per_cycle c_single_packet_per_cycle;
 
initial begin
#1 if (enable_c_single_packet_per_cycle && USE_PACKET && ST_BEATSPERCYCLE > 1) begin
c_single_packet_per_cycle = new();
end
end
//-------------------------------------------------------------------------------
// =head3 c_idle_beat_between_packet
// This cover group covers packet transaction that owns idle beats in between.
//-------------------------------------------------------------------------------
 
covergroup cg_idle_beat_between_packet;
cp_idle_beat_between_packet: coverpoint invalid_beat_between_packet
{
bins cg_idle_beat_between_packet_cp_idle_beat_between_packet = {1};
}
option.per_instance = 1;
endgroup
 
cg_idle_beat_between_packet c_idle_beat_between_packet;
 
initial begin
#1 if (enable_c_idle_beat_between_packet && USE_PACKET && USE_VALID && (ST_BEATSPERCYCLE > 1)) begin
c_idle_beat_between_packet = new();
end
end
//-------------------------------------------------------------------------------
// =head3 c_all_valid_beats
// This cover group covers number of transaction with all beats are valid.
//-------------------------------------------------------------------------------
 
covergroup cg_all_valid_beats;
cp_all_valid_beats: coverpoint all_valid_beats_flag
{
bins cg_all_valid_beats_cp_all_valid_beats = {1};
}
option.per_instance = 1;
endgroup
 
cg_all_valid_beats c_all_valid_beats;
 
initial begin
#1 if (enable_c_all_valid_beats && USE_VALID && (ST_BEATSPERCYCLE > 1)) begin
c_all_valid_beats = new();
end
end
//-------------------------------------------------------------------------------
// =head3 c_all_idle_beats
// This cover group covers number of transaction with all beats are idle.
//-------------------------------------------------------------------------------
 
covergroup cg_all_idle_beats;
cp_all_idle_beats: coverpoint all_invalid_beats_flag
{
bins cg_all_idle_beats_cp_all_idle_beats = {1};
}
option.per_instance = 1;
endgroup
 
cg_all_idle_beats c_all_idle_beats;
 
initial begin
#1 if (enable_c_all_idle_beats && USE_VALID && (ST_BEATSPERCYCLE > 1)) begin
c_all_idle_beats = new();
end
end
//-------------------------------------------------------------------------------
// =head3 c_partial_valid_beats
// This cover group covers number of transaction with some beats are invalid and
// some beats are valid.
//-------------------------------------------------------------------------------
 
covergroup cg_partial_valid_beats;
cp_partial_valid_beats: coverpoint partial_valid_beats_flag
{
bins cg_partial_valid_beats_cp_partial_valid_beats = {1};
}
option.per_instance = 1;
endgroup
 
cg_partial_valid_beats c_partial_valid_beats;
 
initial begin
#1 if (enable_c_partial_valid_beats && USE_VALID && (ST_BEATSPERCYCLE > 1)) begin
c_partial_valid_beats = new();
end
end
//-------------------------------------------------------------------------------
// =head3 c_b2b_packet_within_single_cycle
// This cover group covers back to back packet transfer within single cycle.
//-------------------------------------------------------------------------------
 
covergroup cg_b2b_packet_within_single_cycle;
cp_b2b_packet_within_single_cycle: coverpoint idles_between_b2b_packet_transaction_counter
{
bins cg_b2b_packet_within_single_cycle_cp_b2b_packet_within_single_cycle = {0};
}
option.per_instance = 1;
endgroup
 
cg_b2b_packet_within_single_cycle c_b2b_packet_within_single_cycle;
 
initial begin
#1 if (enable_c_b2b_packet_within_single_cycle && USE_PACKET && USE_VALID && (ST_BEATSPERCYCLE > 1)) begin
c_b2b_packet_within_single_cycle = new();
end
end
//-------------------------------------------------------------------------------
// =head3 c_b2b_packet_in_different_cycle
// This cover group covers back to back packet transfer in different cycle.
//-------------------------------------------------------------------------------
 
covergroup cg_b2b_packet_in_different_cycle;
cp_b2b_packet_in_different_cycle: coverpoint idles_between_b2b_packet_transaction_counter
{
bins cg_b2b_packet_in_different_cycle_cp_b2b_packet_in_different_cycle = {0};
}
option.per_instance = 1;
endgroup
 
cg_b2b_packet_in_different_cycle c_b2b_packet_in_different_cycle;
 
initial begin
#1 if (enable_c_b2b_packet_in_different_cycle && USE_PACKET && USE_VALID && (ST_BEATSPERCYCLE > 1)) begin
c_b2b_packet_in_different_cycle = new();
end
end
//-------------------------------------------------------------------------------
// =head3 c_error_in_middle_of_packet
// This cover group covers assert error in the middle of a packet.
//-------------------------------------------------------------------------------
 
covergroup cg_error_in_middle_of_packet;
cp_error_in_middle_of_packet: coverpoint error_in_middle_of_packet
{
bins cg_error_in_middle_of_packet_cp_error_in_middle_of_packet = {1};
}
option.per_instance = 1;
endgroup
 
cg_error_in_middle_of_packet c_error_in_middle_of_packet;
 
initial begin
#1 if (enable_c_error_in_middle_of_packet && USE_PACKET && USE_ERROR) begin
c_error_in_middle_of_packet = new();
end
end
// =cut
//--------------------------------------------------------------------------
// COVERAGE CODE END
//--------------------------------------------------------------------------
`endif
// synthesis translate_on
endmodule
 
 
/ast_monitor/altera_avalon_st_monitor_171/sim/altera_avalon_st_monitor_transactions.sv
0,0 → 1,404
// (C) 2001-2017 Intel Corporation. All rights reserved.
// Your use of Intel Corporation's design tools, logic functions and other
// software and tools, and its AMPP partner logic functions, and any output
// files from any of the foregoing (including device programming or simulation
// files), and any associated documentation or information are expressly subject
// to the terms and conditions of the Intel Program License Subscription
// Agreement, Intel FPGA IP License Agreement, or other applicable
// license agreement, including, without limitation, that your use is for the
// sole purpose of programming logic devices manufactured by Intel and sold by
// Intel or its authorized distributors. Please refer to the applicable
// agreement for further details.
 
 
// $File: //acds/rel/17.1std/ip/sopc/components/verification/altera_avalon_st_monitor_bfm/altera_avalon_st_monitor_transactions.sv $
// $Revision: #1 $
// $Date: 2017/07/30 $
// $Author: swbranch $
//-----------------------------------------------------------------------------
// =head1 NAME
// altera_avalon_st_monitor_transactions
// =head1 SYNOPSIS
// Streaming Avalon Bus Protocol Checker
//-----------------------------------------------------------------------------
// =head1 DESCRIPTION
// This module implements Avalon ST protocol transaction recording.
//-----------------------------------------------------------------------------
 
`timescale 1ns / 1ns
 
module altera_avalon_st_monitor_transactions(
clk,
reset,
tap
);
 
// =head1 PARAMETERS
parameter ST_SYMBOL_W = 8; // number of bits in one symbols
parameter ST_NUMSYMBOLS = 4; // number of symbols in one data
parameter ST_CHANNEL_W = 0; // width of channel signal
parameter ST_ERROR_W = 0; // width of error signal
parameter ST_EMPTY_W = 0; // width of empty signal
parameter ST_READY_LATENCY = 0; // fixed ready latency in cycles
parameter ST_MAX_CHANNELS = 1; // maximum number of channels
parameter USE_PACKET = 0; // data transfer in packet format
parameter USE_CHANNEL = 0; // use channel port
parameter USE_ERROR = 0; // use error port
parameter USE_READY = 1; // use ready port
parameter USE_VALID = 1; // use valid port
parameter USE_EMPTY = 0; // use empty port
parameter ST_BEATSPERCYCLE = 1; // Max number of packets per cycle
parameter ST_MAX_PACKET_SIZE = 1; // Max number of packet size covered
 
localparam ST_DATA_W = ST_SYMBOL_W * ST_NUMSYMBOLS;
localparam ST_MDATA_W = ST_BEATSPERCYCLE * ST_DATA_W;
localparam ST_MCHANNEL_W = ST_BEATSPERCYCLE * ST_CHANNEL_W;
localparam ST_MERROR_W = ST_BEATSPERCYCLE * ST_ERROR_W;
localparam ST_MEMPTY_W = ST_BEATSPERCYCLE * ST_EMPTY_W;
localparam ST_MAX_EMPTY = 2**(ST_EMPTY_W) - 1;
localparam NUM_CHANNEL = (ST_MAX_CHANNELS > 1)? ST_MAX_CHANNELS:1;
localparam FIFO_MAX_LEVEL = 100;
localparam FIFO_THRESHOLD = 50;
localparam TAP_W = ((ST_DATA_W == 0)? 1:ST_DATA_W) + // data
((ST_CHANNEL_W == 0)? 1:ST_CHANNEL_W) + // channel
1 + // valid
1 + // startofpacket
1 + // endofpacket
((ST_ERROR_W == 0)? 1:ST_ERROR_W) + // error
((ST_EMPTY_W == 0)? 1:ST_EMPTY_W) + // empty
1; // ready
// =head1 PINS
// =head2 Clock Interface
input clk;
input reset;
 
// =head2 Avalon Monitor Interface - will be defined as Streaming Sink
input [(TAP_W*ST_BEATSPERCYCLE)-ST_BEATSPERCYCLE:0] tap;
 
// =cut
function int lindex;
// returns the left index for a vector having a declared width
// when width is 0, then the left index is set to 0 rather than -1
input [31:0] width;
lindex = (width > 0) ? (width-1) : 0;
endfunction
 
//--------------------------------------------------------------------------
// synthesis translate_off
 
import verbosity_pkg::*;
 
//--------------------------------------------------------------------------
// Private Types and Variables
//--------------------------------------------------------------------------
typedef logic [lindex(ST_DATA_W) :0] STData_t;
typedef logic [lindex(ST_CHANNEL_W) :0] STChannel_t;
typedef logic [lindex(ST_EMPTY_W) :0] STEmpty_t;
typedef logic [lindex(ST_ERROR_W) :0] STError_t;
 
typedef logic [lindex(ST_MDATA_W) :0] STMData_t;
typedef logic [lindex(ST_MCHANNEL_W) :0] STMChannel_t;
typedef logic [lindex(ST_MEMPTY_W) :0] STMEmpty_t;
typedef logic [lindex(ST_MERROR_W) :0] STMError_t;
typedef logic [ST_BEATSPERCYCLE-1 :0] STBeats_t;
typedef struct packed
{
bit [31:0] idles;
logic startofpacket;
logic endofpacket;
STChannel_t channel;
STData_t data;
STError_t error;
STEmpty_t empty;
} Transaction_t;
Transaction_t current_transaction[ST_BEATSPERCYCLE];
Transaction_t query_transaction;
Transaction_t transaction_queue[$];
 
// unpack Avalon bus interface tap into individual port signals
logic [lindex(ST_MDATA_W): 0] sink_data;
logic [lindex(ST_MCHANNEL_W): 0] sink_channel;
logic [ST_BEATSPERCYCLE-1: 0] sink_valid;
logic [ST_BEATSPERCYCLE-1: 0] sink_startofpacket;
logic [ST_BEATSPERCYCLE-1: 0] sink_endofpacket;
logic [lindex(ST_MERROR_W): 0] sink_error;
logic [lindex(ST_MEMPTY_W): 0] sink_empty;
logic sink_ready;
string message = "*uninitialized*";
logic ready = 0;
int idle_ctr = 0;
int transaction_fifo_max = FIFO_MAX_LEVEL;
int transaction_fifo_threshold = FIFO_THRESHOLD;
STBeats_t sink_valid_qualified;
logic sink_ready_qualified;
 
localparam MAX_READY_DELAY = 8;
logic [MAX_READY_DELAY-1:0] sink_ready_delayed;
 
//--------------------------------------------------------------------------
// Private Functions
//--------------------------------------------------------------------------
function int __floor(int arg);
// returns the arg if it is greater than 0, else returns 0
return (arg > 0) ? arg : 0;
endfunction
//--------------------------------------------------------------------------
// =head1 Public Methods API
// This section describes the public methods in the application programming
// interface (API). In this case the application program is the test bench
// which instantiates and controls and queries state of this component.
// Test programs must only use these public access methods and events to
// communicate with this BFM component. The API and the module pins
// are the only interfaces in this component that are guaranteed to be
// stable. The API will be maintained for the life of the product.
// While we cannot prevent a test program from directly accessing internal
// tasks, functions, or data private to the BFM, there is no guarantee that
// these will be present in the future. In fact, it is best for the user
// to assume that the underlying implementation of this component can
// and will change.
//--------------------------------------------------------------------------
event signal_fatal_error; // public
// Signal that a fatal error has occurred. Terminates simulation.
event signal_transaction_received; //public
// Signal that a transaction has been received and queued.
 
event signal_transaction_fifo_threshold; // public
// Signal that the transaction FIFO threshold level has been exceeded
 
event signal_transaction_fifo_overflow; // public
// Signal that the FIFO is full and further transactions are being dropped
function automatic string get_version(); // public
// Return component version as a string of three integers separated by periods.
// For example, version 9.1 sp1 is encoded as "9.1.1".
string ret_version = "17.1";
return ret_version;
endfunction
 
function automatic void set_transaction_fifo_max( // public
int level
);
// Set the maximum fullness level of the FIFO. The event
// signal_transaction_fifo_max is triggered when this
// level is exceeded.
transaction_fifo_max = level;
endfunction
 
function automatic int get_transaction_fifo_max();
// Get the maximum transaction FIFO depth.
return transaction_fifo_max;
endfunction
function automatic void set_transaction_fifo_threshold( // public
int level
);
// Set the threshold alert level of the FIFO. The event
// signal_transaction_fifo_threshold is triggered when this
// level is exceeded.
transaction_fifo_threshold = level;
endfunction
 
function automatic int get_transaction_fifo_threshold();
// Get the transaction FIFO threshold level.
return transaction_fifo_threshold;
endfunction
function automatic void pop_transaction(); // public
// Pop the transaction descriptor from the queue so that it can be
// queried with the get_transaction methods by the test bench.
if (reset) begin
$sformat(message, "%m: Illegal command while reset asserted");
print(VERBOSITY_ERROR, message);
->signal_fatal_error;
end
query_transaction = transaction_queue.pop_back();
 
$sformat(message, "%m: called pop_transaction");
print(VERBOSITY_DEBUG, message);
$sformat(message, "%m: Data: %x", query_transaction.data);
print(VERBOSITY_DEBUG, message);
$sformat(message, "%m: Channel: %0d", query_transaction.channel);
print(VERBOSITY_DEBUG, message);
$sformat(message, "%m: SOP: %0d EOP: %0d",
query_transaction.startofpacket,
query_transaction.endofpacket);
print(VERBOSITY_DEBUG, message);
endfunction
 
function automatic bit[31:0] get_transaction_idles(); // public
// Return the number of idle cycles in the transaction
$sformat(message, "%m: called get_transaction_idles");
print(VERBOSITY_DEBUG, message);
return query_transaction.idles;
endfunction
 
function automatic logic [ST_DATA_W-1:0] get_transaction_data(); // public
// Return the data in the transaction
$sformat(message, "%m: called get_transaction_data");
print(VERBOSITY_DEBUG, message);
return query_transaction.data;
endfunction
function automatic logic [ST_CHANNEL_W-1:0] get_transaction_channel(); // public
// Return the channel identifier in the transaction
$sformat(message, "%m: called get_transaction_channel");
print(VERBOSITY_DEBUG, message);
return query_transaction.channel;
endfunction
 
function automatic logic get_transaction_sop(); // public
// Return the start of packet status in the transaction
$sformat(message, "%m: called get_transaction_sop");
print(VERBOSITY_DEBUG, message);
return query_transaction.startofpacket;
endfunction
 
function automatic logic get_transaction_eop(); // public
// Return the end of packet status in the transaction
$sformat(message, "%m: called get_transaction_eop");
print(VERBOSITY_DEBUG, message);
return query_transaction.endofpacket;
endfunction
 
function automatic logic [ST_ERROR_W-1:0] get_transaction_error(); // public
// Return the error status in the transaction
$sformat(message, "%m: called get_transaction_error");
print(VERBOSITY_DEBUG, message);
return query_transaction.error;
endfunction
 
function automatic logic [ST_EMPTY_W-1:0] get_transaction_empty(); // public
// Return the number of empty symbols in the transaction
$sformat(message, "%m: called get_transaction_empty");
print(VERBOSITY_DEBUG, message);
return query_transaction.empty;
endfunction
 
function automatic int get_transaction_queue_size(); // public
// Return the length of the queue holding received transactions
$sformat(message, "%m: called get_transaction_queue_size");
print(VERBOSITY_DEBUG, message);
// Return the number of transactions in the internal queues.
return transaction_queue.size();
endfunction
// =cut
 
//--------------------------------------------------------------------------
// Local Machinery
//--------------------------------------------------------------------------
always @(signal_fatal_error) abort_simulation();
always @(*) begin
{
sink_data,
sink_channel,
sink_valid,
sink_startofpacket,
sink_endofpacket,
sink_error,
sink_empty,
sink_ready
} <= tap;
end
// delay chain for sink_ready back pressure output to account for latency
always @(posedge clk or posedge reset) begin
if (reset) begin
sink_ready_delayed <= 0;
end else begin
sink_ready_delayed <= {sink_ready_delayed[6:0], sink_ready};
end
end
 
always @(*) begin
if (USE_READY == 0)
sink_ready_qualified = 1'b1;
else begin
if (ST_READY_LATENCY == 0)
sink_ready_qualified = sink_ready;
else
sink_ready_qualified = sink_ready_delayed[__floor(ST_READY_LATENCY-1)];
end
end
always @(sink_valid) begin
if (USE_VALID > 0)
sink_valid_qualified = sink_valid;
else
sink_valid_qualified = '1;
end
always @(posedge clk or posedge reset) begin
if (reset) begin
for (int i=0; i<ST_BEATSPERCYCLE; i++) begin
current_transaction[i] = '0;
end
end else begin
if (sink_ready_qualified) begin
if (sink_valid_qualified != 0)
->signal_transaction_received;
for (int i=0; i<ST_BEATSPERCYCLE; i++) begin
if (sink_valid_qualified[i]) begin
current_transaction[i].data =
sink_data >> (i*ST_DATA_W);
current_transaction[i].channel =
sink_channel >> (i*ST_CHANNEL_W);
current_transaction[i].startofpacket =
sink_startofpacket[i];
current_transaction[i].endofpacket =
sink_endofpacket[i];
current_transaction[i].error =
sink_error >> (i*ST_ERROR_W);
current_transaction[i].empty =
sink_empty >> (i*ST_EMPTY_W);
 
// TODO - this is ok for single beat, but not for multi beats
current_transaction[i].idles = idle_ctr; // replicate
 
if (get_transaction_queue_size() < transaction_fifo_max) begin
transaction_queue.push_front(current_transaction[i]);
 
if (get_transaction_queue_size() > transaction_fifo_threshold)
->signal_transaction_fifo_threshold;
end else begin
$sformat(message,
"%m: FIFO overflow! Transaction dropped.");
print(VERBOSITY_WARNING, message);
->signal_transaction_fifo_overflow;
end
end
end
end
end
end
// synthesis translate_on
endmodule
 
 
/ast_monitor/altera_avalon_st_monitor_171/sim/avalon_utilities_pkg.sv
0,0 → 1,80
// (C) 2001-2017 Intel Corporation. All rights reserved.
// Your use of Intel Corporation's design tools, logic functions and other
// software and tools, and its AMPP partner logic functions, and any output
// files from any of the foregoing (including device programming or simulation
// files), and any associated documentation or information are expressly subject
// to the terms and conditions of the Intel Program License Subscription
// Agreement, Intel FPGA IP License Agreement, or other applicable
// license agreement, including, without limitation, that your use is for the
// sole purpose of programming logic devices manufactured by Intel and sold by
// Intel or its authorized distributors. Please refer to the applicable
// agreement for further details.
 
 
// $Id: //acds/rel/17.1std/ip/sopc/components/verification/lib/avalon_utilities_pkg.sv#1 $
// $Revision: #1 $
// $Date: 2017/07/30 $
//-----------------------------------------------------------------------------
// =head1 NAME
// avalon_utilities_pkg
// =head1 SYNOPSIS
// Package for shared types and functions
//-----------------------------------------------------------------------------
// =head1 COPYRIGHT
// Copyright (c) 2008 Altera Corporation. All Rights Reserved.
// The information contained in this file is the property of Altera
// Corporation. Except as specifically authorized in writing by Altera
// Corporation, the holder of this file shall keep all information
// contained herein confidential and shall protect same in whole or in part
// from disclosure and dissemination to all third parties. Use of this
// program confirms your agreement with the terms of this license.
//-----------------------------------------------------------------------------
// =head1 DESCRIPTION
// This package contains shared types and functions.
// =cut
`timescale 1ns / 1ns
 
`ifndef _AVALON_UTILITIES_PKG_
`define _AVALON_UTILITIES_PKG_
 
package avalon_utilities_pkg;
 
function automatic int clog2(
bit [31:0] Depth
);
int i= Depth;
for(clog2 = 0; i > 0; clog2 = clog2 + 1)
i = i >> 1;
 
return clog2;
endfunction
 
function automatic int max(
bit [31:0] one,
bit [31:0] two
);
if(one > two)
return one;
else
return two;
endfunction
 
function automatic int lindex(
bit [31:0] width
);
// returns the left index for a vector having a declared width
// when width is 0, then the left index is set to 0 rather than -1
lindex = (width > 0) ? (width-1) : 0;
endfunction
typedef enum int {
LOW = 0,
HIGH = 1,
RANDOM = 2,
UNKNOWN = 3
} IdleOutputValue_t;
endpackage
 
`endif
/ast_monitor/altera_avalon_st_monitor_171/sim/verbosity_pkg.sv
0,0 → 1,193
// (C) 2001-2017 Intel Corporation. All rights reserved.
// Your use of Intel Corporation's design tools, logic functions and other
// software and tools, and its AMPP partner logic functions, and any output
// files from any of the foregoing (including device programming or simulation
// files), and any associated documentation or information are expressly subject
// to the terms and conditions of the Intel Program License Subscription
// Agreement, Intel FPGA IP License Agreement, or other applicable
// license agreement, including, without limitation, that your use is for the
// sole purpose of programming logic devices manufactured by Intel and sold by
// Intel or its authorized distributors. Please refer to the applicable
// agreement for further details.
 
 
// $Id: //acds/rel/17.1std/ip/sopc/components/verification/lib/verbosity_pkg.sv#1 $
// $Revision: #1 $
// $Date: 2017/07/30 $
//-----------------------------------------------------------------------------
// =head1 NAME
// verbosity_pkg
// =head1 SYNOPSIS
// Package for controlling verbosity of messages sent to the console
//-----------------------------------------------------------------------------
// =head1 COPYRIGHT
// Copyright (c) 2008 Altera Corporation. All Rights Reserved.
// The information contained in this file is the property of Altera
// Corporation. Except as specifically authorized in writing by Altera
// Corporation, the holder of this file shall keep all information
// contained herein confidential and shall protect same in whole or in part
// from disclosure and dissemination to all third parties. Use of this
// program confirms your agreement with the terms of this license.
//-----------------------------------------------------------------------------
// =head1 DESCRIPTION
// This module will dump diagnostic messages to the console during
// simulation. The level of verbosity can be controlled in the test
// bench by using the *set_verbosity* method in the imported package
// verbosity_pkg. For a given setting, message at that level and all
// lower levels are dumped. For example, setting VERBOSITY_DEBUG level
// causes all messages to be dumped, while VERBOSITY_FAILURE restricts
// only failure messages and those tagged as VERBOSITY_NONE to be
// dumped.
// The different levels are:
// =over 4
// =item 1 VERBOSITY_NONE
// Messages tagged with this level are always dumped to the console.
// =item 2 VERBOSITY_FAILURE
// A fatal simulation error has occurred and the simulator will exit.
// =item 3 VERBOSITY_ERROR
// A non-fatal error has occured. An example is a data comparison mismatch.
// =item 4 VERBOSITY_WARNING
// Warn the user that a potential error has occurred.
// =item 5 VERBOSITY_INFO
// Informational message.
// =item 6 VERBOSITY_DEBUG
// Dump enough state to diagnose problem scenarios.
// =back
 
 
`ifndef _AVALON_VERBOSITY_PKG_
`define _AVALON_VERBOSITY_PKG_
 
package verbosity_pkg;
 
timeunit 1ps;
timeprecision 1ps;
typedef enum int {VERBOSITY_NONE,
VERBOSITY_FAILURE,
VERBOSITY_ERROR,
VERBOSITY_WARNING,
VERBOSITY_INFO,
VERBOSITY_DEBUG} Verbosity_t;
 
Verbosity_t verbosity = VERBOSITY_INFO;
string message = "";
int dump_file;
int dump = 0;
 
//--------------------------------------------------------------------------
// =head1 Public Methods API
// =pod
// This section describes the public methods in the application programming
// interface (API). In this case the application program is the test bench
// or component which imports this package.
// =cut
//--------------------------------------------------------------------------
 
function automatic Verbosity_t get_verbosity(); // public
// Returns the global verbosity setting.
return verbosity;
endfunction
 
function automatic void set_verbosity ( // public
Verbosity_t v
);
// Sets the global verbosity setting.
 
string verbosity_str;
verbosity = v;
 
case(verbosity)
VERBOSITY_NONE: verbosity_str = "VERBOSITY_";
VERBOSITY_FAILURE: verbosity_str = "VERBOSITY_FAILURE";
VERBOSITY_ERROR: verbosity_str = "VERBOSITY_ERROR";
VERBOSITY_WARNING: verbosity_str = "VERBOSITY_WARNING";
VERBOSITY_INFO: verbosity_str = "VERBOSITY_INFO";
VERBOSITY_DEBUG: verbosity_str = "VERBOSITY_DEBUG";
default: verbosity_str = "UNKNOWN";
endcase
$sformat(message, "%m: Setting Verbosity level=%0d (%s)",
verbosity, verbosity_str);
print(VERBOSITY_NONE, message);
endfunction
 
function automatic void print( // public
Verbosity_t level,
string message
);
// Print a message to the console if the verbosity argument
// is less than or equal to the global verbosity setting.
string level_str;
 
if (level <= verbosity) begin
case(level)
VERBOSITY_NONE: level_str = "";
VERBOSITY_FAILURE: level_str = "FAILURE:";
VERBOSITY_ERROR: level_str = "ERROR:";
VERBOSITY_WARNING: level_str = "WARNING:";
VERBOSITY_INFO: level_str = "INFO:";
VERBOSITY_DEBUG: level_str = "DEBUG:";
default: level_str = "UNKNOWN:";
endcase
$display("%t: %s %s",$time, level_str, message);
if (dump) begin
$fdisplay(dump_file, "%t: %s %s",$time, level_str, message);
end
end
endfunction
 
function automatic void print_divider( // public
Verbosity_t level
);
// Prints a divider line to the console to make a block of related text
// easier to identify and read.
string message;
$sformat(message,
"------------------------------------------------------------");
print(level, message);
endfunction
function automatic void open_dump_file ( // public
string dump_file_name = "avalon_bfm_sim.log"
);
// Opens a dump file which collects console messages.
if (dump) begin
$sformat(message, "%m: Dump file already open - ignoring open.");
print(VERBOSITY_ERROR, message);
end else begin
dump_file = $fopen(dump_file_name, "w");
$fdisplay(dump_file, "testing dump file");
$sformat(message, "%m: Opening dump file: %s", dump_file_name);
print(VERBOSITY_INFO, message);
dump = 1;
end
endfunction
function automatic void close_dump_file(); // public
// Close the console message dump file.
if (!dump) begin
$sformat(message, "%m: No open dump file - ignoring close.");
print(VERBOSITY_ERROR, message);
end else begin
dump = 0;
$fclose(dump_file);
$sformat(message, "%m: Closing dump file");
print(VERBOSITY_INFO, message);
end
endfunction
 
function automatic void abort_simulation();
string message;
$sformat(message, "%m: Abort the simulation due to fatal error incident.");
print(VERBOSITY_FAILURE, message);
$stop;
endfunction
endpackage
// =cut
 
`endif
/ast_monitor.qsys
0,0 → 1,105
<?xml version="1.0" encoding="UTF-8"?>
<system name="$${FILENAME}">
<component
name="$${FILENAME}"
displayName="$${FILENAME}"
version="1.0"
description=""
tags="INTERNAL_COMPONENT=true"
categories="System" />
<parameter name="bonusData"><![CDATA[bonusData
{
element st_monitor_0
{
datum _sortIndex
{
value = "0";
type = "int";
}
}
}
]]></parameter>
<parameter name="clockCrossingAdapter" value="HANDSHAKE" />
<parameter name="device" value="10AX115S2F45I1SG" />
<parameter name="deviceFamily" value="Arria 10" />
<parameter name="deviceSpeedGrade" value="1" />
<parameter name="fabricMode" value="QSYS" />
<parameter name="generateLegacySim" value="false" />
<parameter name="generationId" value="0" />
<parameter name="globalResetBus" value="false" />
<parameter name="hdlLanguage" value="VERILOG" />
<parameter name="hideFromIPCatalog" value="true" />
<parameter name="lockedInterfaceDefinition" value="" />
<parameter name="maxAdditionalLatency" value="1" />
<parameter name="projectName" value="" />
<parameter name="sopcBorderPoints" value="false" />
<parameter name="systemHash" value="0" />
<parameter name="testBenchDutName" value="" />
<parameter name="timeStamp" value="0" />
<parameter name="useTestBenchNamingPattern" value="false" />
<instanceScript></instanceScript>
<interface name="clk" internal="st_monitor_0.clk" type="clock" dir="end">
<port name="clk" internal="clk" />
</interface>
<interface
name="clk_reset"
internal="st_monitor_0.clk_reset"
type="reset"
dir="end">
<port name="reset" internal="reset" />
</interface>
<interface
name="sink"
internal="st_monitor_0.sink"
type="avalon_streaming"
dir="end">
<port name="sink_data" internal="sink_data" />
<port name="sink_valid" internal="sink_valid" />
<port name="sink_ready" internal="sink_ready" />
<port name="sink_startofpacket" internal="sink_startofpacket" />
<port name="sink_endofpacket" internal="sink_endofpacket" />
<port name="sink_empty" internal="sink_empty" />
<port name="sink_channel" internal="sink_channel" />
<port name="sink_error" internal="sink_error" />
</interface>
<interface
name="src"
internal="st_monitor_0.src"
type="avalon_streaming"
dir="start">
<port name="src_data" internal="src_data" />
<port name="src_valid" internal="src_valid" />
<port name="src_ready" internal="src_ready" />
<port name="src_startofpacket" internal="src_startofpacket" />
<port name="src_endofpacket" internal="src_endofpacket" />
<port name="src_empty" internal="src_empty" />
<port name="src_channel" internal="src_channel" />
<port name="src_error" internal="src_error" />
</interface>
<module
name="st_monitor_0"
kind="altera_avalon_st_monitor"
version="17.1"
enabled="1"
autoexport="1">
<parameter name="ST_BEATSPERCYCLE" value="1" />
<parameter name="ST_CHANNEL_W" value="2" />
<parameter name="ST_ERROR_W" value="1" />
<parameter name="ST_MAX_CHANNELS" value="3" />
<parameter name="ST_MAX_PACKET_SIZE" value="4" />
<parameter name="ST_NUMSYMBOLS" value="4" />
<parameter name="ST_READY_LATENCY" value="4" />
<parameter name="ST_SYMBOL_W" value="8" />
<parameter name="USE_CHANNEL" value="1" />
<parameter name="USE_EMPTY" value="1" />
<parameter name="USE_ERROR" value="1" />
<parameter name="USE_PACKET" value="1" />
<parameter name="USE_READY" value="1" />
<parameter name="USE_VALID" value="1" />
<parameter name="VHDL_ID" value="0" />
</module>
<interconnectRequirement for="$system" name="qsys_mm.clockCrossingAdapter" value="HANDSHAKE" />
<interconnectRequirement for="$system" name="qsys_mm.enableEccProtection" value="FALSE" />
<interconnectRequirement for="$system" name="qsys_mm.insertDefaultSlave" value="FALSE" />
<interconnectRequirement for="$system" name="qsys_mm.maxAdditionalLatency" value="1" />
</system>
/ast_sink/altera_avalon_st_sink_bfm_171/sim/altera_avalon_st_sink_bfm.sv
0,0 → 1,463
// (C) 2001-2017 Intel Corporation. All rights reserved.
// Your use of Intel Corporation's design tools, logic functions and other
// software and tools, and its AMPP partner logic functions, and any output
// files from any of the foregoing (including device programming or simulation
// files), and any associated documentation or information are expressly subject
// to the terms and conditions of the Intel Program License Subscription
// Agreement, Intel FPGA IP License Agreement, or other applicable
// license agreement, including, without limitation, that your use is for the
// sole purpose of programming logic devices manufactured by Intel and sold by
// Intel or its authorized distributors. Please refer to the applicable
// agreement for further details.
 
 
// $File: //acds/rel/17.1std/ip/sopc/components/verification/altera_avalon_st_sink_bfm/altera_avalon_st_sink_bfm.sv $
// $Revision: #1 $
// $Date: 2017/07/30 $
// $Author: swbranch $
//-----------------------------------------------------------------------------
// =head1 NAME
// altera_avalon_st_sink_bfm
// =head1 SYNOPSIS
// Bus Functional Model (BFM) for a Avalon Streaming Sink
//-----------------------------------------------------------------------------
// =head1 DESCRIPTION
// This is a Bus Functional Model (BFM) for a Avalon Streaming Sink.
// The behavior of each clock cycle of the ST protocol on the interface
// is governed by a transaction. Received bus cycles are captured as
// transactions and pushed into a response queue. Clients query received
// transactions by popping them off the queue one by one and extract
// information using the public API methods provided. Back pressure to
// a driving source is also applied using the API method set_ready.
//-----------------------------------------------------------------------------
 
`timescale 1ps / 1ps
 
module altera_avalon_st_sink_bfm(
clk,
reset,
sink_data,
sink_channel,
sink_valid,
sink_startofpacket,
sink_endofpacket,
sink_error,
sink_empty,
sink_ready
);
// =head1 PARAMETERS
parameter ST_SYMBOL_W = 8; // Data symbol width in bits
parameter ST_NUMSYMBOLS = 4; // Number of symbols per word
parameter ST_CHANNEL_W = 0; // Channel width in bits
parameter ST_ERROR_W = 0; // Error width in bits
parameter ST_EMPTY_W = 0; // Empty width in bits
parameter ST_READY_LATENCY = 0; // Number of cycles latency after ready (0 or 1 only)
parameter ST_MAX_CHANNELS = 1; // Maximum number of channels
parameter USE_PACKET = 0; // Use packet pins on interface
parameter USE_CHANNEL = 0; // Use channel pins on interface
parameter USE_ERROR = 0; // Use error pin on interface
parameter USE_READY = 1; // Use ready pin on interface
parameter USE_VALID = 1; // Use valid pin on interface
parameter USE_EMPTY = 0; // Use empty pin on interface
 
parameter ST_BEATSPERCYCLE = 1; // Max number of packets per cycle
parameter VHDL_ID = 0; // VHDL BFM ID number
localparam ST_DATA_W = ST_SYMBOL_W * ST_NUMSYMBOLS;
localparam ST_MDATA_W = ST_BEATSPERCYCLE * ST_DATA_W;
localparam ST_MCHANNEL_W = ST_BEATSPERCYCLE * ST_CHANNEL_W;
localparam ST_MERROR_W = ST_BEATSPERCYCLE * ST_ERROR_W;
localparam ST_MEMPTY_W = ST_BEATSPERCYCLE * ST_EMPTY_W;
 
// =head1 PINS
// =head2 Clock Interface
input clk;
input reset;
 
// =head2 Avalon Streaming Source Interface
input [lindex(ST_MDATA_W): 0] sink_data;
input [lindex(ST_MCHANNEL_W): 0] sink_channel;
input [ST_BEATSPERCYCLE-1: 0] sink_valid;
input [ST_BEATSPERCYCLE-1: 0] sink_startofpacket;
input [ST_BEATSPERCYCLE-1: 0] sink_endofpacket;
input [lindex(ST_MERROR_W): 0] sink_error;
input [lindex(ST_MEMPTY_W): 0] sink_empty;
output sink_ready;
 
// =cut
function integer lindex;
// returns the left index for a vector having a declared width
// when width is 0, then the left index is set to 0 rather than -1
input [31:0] width;
lindex = (width > 0) ? (width-1) : 0;
endfunction
// synthesis translate_off
import verbosity_pkg::*;
logic sink_ready;
//--------------------------------------------------------------------------
// Private Types and Variables
//--------------------------------------------------------------------------
 
typedef logic [lindex(ST_DATA_W) :0] STData_t;
typedef logic [lindex(ST_CHANNEL_W) :0] STChannel_t;
typedef logic [lindex(ST_EMPTY_W) :0] STEmpty_t;
typedef logic [lindex(ST_ERROR_W) :0] STError_t;
 
typedef logic [lindex(ST_MDATA_W) :0] STMData_t;
typedef logic [lindex(ST_MCHANNEL_W) :0] STMChannel_t;
typedef logic [lindex(ST_MEMPTY_W) :0] STMEmpty_t;
typedef logic [lindex(ST_MERROR_W) :0] STMError_t;
typedef logic [ST_BEATSPERCYCLE-1 :0] STBeats_t;
typedef struct packed
{
bit [31:0] idles;
logic startofpacket;
logic endofpacket;
STChannel_t channel;
STData_t data;
STError_t error;
STEmpty_t empty;
} Transaction_t;
Transaction_t current_transaction[ST_BEATSPERCYCLE];
Transaction_t query_transaction;
 
Transaction_t transaction_queue[$];
 
string message = "*uninitialized*";
logic ready = 0;
int idle_ctr = 0;
 
STBeats_t sink_valid_qualified;
logic sink_ready_qualified;
 
localparam MAX_READY_DELAY = 8;
logic [MAX_READY_DELAY-1:0] sink_ready_delayed;
 
//--------------------------------------------------------------------------
// =head1 Public Methods API
// =pod
// This section describes the public methods in the application programming
// interface (API). In this case the application program is the test bench
// which instantiates and controls and queries state in this BFM component.
// Test programs must only use these public access methods and events to
// communicate with this BFM component. The API and the module pins
// are the only interfaces in this component that are guaranteed to be
// stable. The API will be maintained for the life of the product.
// While we cannot prevent a test program from directly accessing internal
// tasks, functions, or data private to the BFM, there is no guarantee that
// these will be present in the future. In fact, it is best for the user
// to assume that the underlying implementation of this component can
// and will change.
// =cut
//--------------------------------------------------------------------------
 
event signal_fatal_error; // public
// Signal that a fatal error has occurred. Terminates simulation.
event signal_transaction_received; //public
// Signal that a transaction has been received and queued.
 
event signal_sink_ready_assert; // public
// Signal that sink_ready is asserted thereby turning off back pressure.
event signal_sink_ready_deassert; // public
// Signal that sink_ready is deasserted thereby turning on back pressure.
 
function automatic string get_version(); // public
// Return BFM version string. For example, version 9.1 sp1 is "9.1sp1"
string ret_version = "__ACDS_VERSION_SHORT__";
return ret_version;
endfunction
task automatic init(); // public
// Drive interface to idle state.
$sformat(message, "%m: called init");
print(VERBOSITY_DEBUG, message);
drive_interface_idle();
endtask
 
task automatic set_ready( // public
bit state
);
// Set the value of the interface ready signal. To assert back
// pressure, the state argument is set to 0 i.e. not ready.
// The parameter USE_READY must be set to 1 to enable this signal.
if (USE_READY > 0) begin
$sformat(message, "%m: called set_ready");
print(VERBOSITY_DEBUG, message);
sink_ready <= state;
 
if (state == 1'b1)
->signal_sink_ready_assert;
else
->signal_sink_ready_deassert;
end else begin
$sformat(message, "%m: Ignore set_ready() when USE_READY == 0");
print(VERBOSITY_WARNING, message);
sink_ready <= 0;
end
endtask
function automatic void pop_transaction(); // public
// Pop the transaction descriptor from the queue so that it can be
// queried with the get_transaction methods by the test bench.
if (reset) begin
$sformat(message, "%m: Illegal command while reset asserted");
print(VERBOSITY_ERROR, message);
->signal_fatal_error;
end
query_transaction = transaction_queue.pop_back();
 
$sformat(message, "%m: called pop_transaction");
print(VERBOSITY_DEBUG, message);
$sformat(message, "%m: Data: %x", query_transaction.data);
print(VERBOSITY_DEBUG, message);
$sformat(message, "%m: Channel: %0d", query_transaction.channel);
print(VERBOSITY_DEBUG, message);
$sformat(message, "%m: SOP: %0d EOP: %0d",
query_transaction.startofpacket,
query_transaction.endofpacket);
print(VERBOSITY_DEBUG, message);
endfunction
 
function automatic bit[31:0] get_transaction_idles(); // public
// Return the number of idle cycles in the transaction
$sformat(message, "%m: called get_transaction_idles");
print(VERBOSITY_DEBUG, message);
return query_transaction.idles;
endfunction
 
function automatic logic [ST_DATA_W-1:0] get_transaction_data(); // public
// Return the data in the transaction
$sformat(message, "%m: called get_transaction_data");
print(VERBOSITY_DEBUG, message);
return query_transaction.data;
endfunction
function automatic logic [ST_CHANNEL_W-1:0] get_transaction_channel(); // public
// Return the channel identifier in the transaction
$sformat(message, "%m: called get_transaction_channel");
print(VERBOSITY_DEBUG, message);
return query_transaction.channel;
endfunction
 
function automatic logic get_transaction_sop(); // public
// Return the start of packet status in the transaction
$sformat(message, "%m: called get_transaction_sop");
print(VERBOSITY_DEBUG, message);
return query_transaction.startofpacket;
endfunction
 
function automatic logic get_transaction_eop(); // public
// Return the end of packet status in the transaction
$sformat(message, "%m: called get_transaction_eop");
print(VERBOSITY_DEBUG, message);
return query_transaction.endofpacket;
endfunction
 
function automatic logic [ST_ERROR_W-1:0] get_transaction_error(); // public
// Return the error status in the transaction
$sformat(message, "%m: called get_transaction_error");
print(VERBOSITY_DEBUG, message);
return query_transaction.error;
endfunction
 
function automatic logic [ST_EMPTY_W-1:0] get_transaction_empty(); // public
// Return the number of empty symbols in the transaction
$sformat(message, "%m: called get_transaction_empty");
print(VERBOSITY_DEBUG, message);
return query_transaction.empty;
endfunction
 
function automatic int get_transaction_queue_size(); // public
// Return the length of the queue holding received transactions
$sformat(message, "%m: called get_transaction_queue_size");
print(VERBOSITY_DEBUG, message);
// Return the number of transactions in the internal queues.
return transaction_queue.size();
endfunction
 
// =cut
//--------------------------------------------------------------------------
// Private Methods
//--------------------------------------------------------------------------
function int __floor(
int arg
);
// returns the arg if it is greater than 0, else returns 0
return (arg > 0) ? arg : 0;
endfunction
 
task automatic drive_interface_idle();
set_ready(0);
endtask
 
function automatic void __hello();
// Introduction Message to console
$sformat(message, "%m: - Hello from altera_avalon_st_sink_bfm.");
print(VERBOSITY_INFO, message);
$sformat(message, "%m: - $Revision: #1 $");
print(VERBOSITY_INFO, message);
$sformat(message, "%m: - $Date: 2017/07/30 $");
print(VERBOSITY_INFO, message);
$sformat(message, "%m: - ST_SYMBOL_W = %0d",
ST_SYMBOL_W);
print(VERBOSITY_INFO, message);
$sformat(message, "%m: - ST_NUMSYMBOLS = %0d",
ST_NUMSYMBOLS);
print(VERBOSITY_INFO, message);
$sformat(message, "%m: - ST_CHANNEL_W = %0d",
ST_CHANNEL_W);
print(VERBOSITY_INFO, message);
$sformat(message, "%m: - ST_ERROR_W = %0d",
ST_ERROR_W);
print(VERBOSITY_INFO, message);
$sformat(message, "%m: - ST_EMPTY_W = %0d",
ST_EMPTY_W);
print(VERBOSITY_INFO, message);
$sformat(message, "%m: - ST_READY_LATENCY = %0d",
ST_READY_LATENCY);
print(VERBOSITY_INFO, message);
$sformat(message, "%m: - ST_MAX_CHANNELS = %0d",
ST_MAX_CHANNELS);
print(VERBOSITY_INFO, message);
$sformat(message, "%m: - ST_BEATSPERCYCLE = %0d",
ST_BEATSPERCYCLE);
print(VERBOSITY_INFO, message);
$sformat(message, "%m: - USE_PACKET = %0d",
USE_PACKET);
print(VERBOSITY_INFO, message);
$sformat(message, "%m: - USE_CHANNEL = %0d",
USE_CHANNEL);
print(VERBOSITY_INFO, message);
$sformat(message, "%m: - USE_ERROR = %0d",
USE_ERROR);
print(VERBOSITY_INFO, message);
$sformat(message, "%m: - USE_READY = %0d",
USE_READY);
print(VERBOSITY_INFO, message);
$sformat(message, "%m: - USE_VALID = %0d",
USE_VALID);
print(VERBOSITY_INFO, message);
$sformat(message, "%m: - USE_EMPTY = %0d",
USE_EMPTY);
print(VERBOSITY_INFO, message);
print_divider(VERBOSITY_INFO);
endfunction
 
//--------------------------------------------------------------------------
initial begin
__hello();
end
//--------------------------------------------------------------------------
// Local Machinery
//--------------------------------------------------------------------------
always @(signal_fatal_error) abort_simulation();
// delay chain for sink_ready back pressure output to account for latency
always @(posedge clk or posedge reset) begin
if (reset) begin
sink_ready_delayed <= 0;
end else begin
sink_ready_delayed <= {sink_ready_delayed[6:0], sink_ready};
end
end
 
assign sink_ready_qualified = (USE_READY == 0)? 1'b1 :
(ST_READY_LATENCY == 0)? sink_ready :
sink_ready_delayed[__floor(ST_READY_LATENCY-1)];
 
assign sink_valid_qualified = (USE_VALID == 0)? 1'b1 : sink_valid;
 
always @(posedge clk or posedge reset) begin
if (reset) begin
transaction_queue = {};
query_transaction = 0;
for (int i=0; i<ST_BEATSPERCYCLE; i++) begin
current_transaction[i] = '0;
end
end else begin
if (sink_ready_qualified) begin
if (sink_valid_qualified != 0)
->signal_transaction_received;
for (int i=0; i<ST_BEATSPERCYCLE; i++) begin
if (sink_valid_qualified[i]) begin
current_transaction[i].data =
sink_data >> (i*ST_DATA_W);
current_transaction[i].channel =
sink_channel >> (i*ST_CHANNEL_W);
current_transaction[i].startofpacket =
sink_startofpacket[i];
current_transaction[i].endofpacket =
sink_endofpacket[i];
current_transaction[i].error =
sink_error >> (i*ST_ERROR_W);
current_transaction[i].empty =
sink_empty >> (i*ST_EMPTY_W);
 
// TODO - this is ok for single beat, but not for multi beats
current_transaction[i].idles = idle_ctr; // replicate
 
transaction_queue.push_front(current_transaction[i]);
end
end
end
end
end
 
bit sink_ready_d1;
always @(posedge clk or posedge reset) begin
if (reset)
sink_ready_d1 <= 0;
else
sink_ready_d1 <= sink_ready_qualified;
end
always @(posedge clk or posedge reset) begin
if (reset) begin
idle_ctr <= 0;
end else if (ST_BEATSPERCYCLE == 1) begin
if (sink_ready_d1 && ~sink_valid_qualified[0]) begin
idle_ctr <= idle_ctr + 1;
end else begin
idle_ctr <= 0;
end
end else begin
// TODO - compute idle bubbles with multiple beats/cycle
idle_ctr <= 0;
end
end
// synthesis translate_on
 
endmodule
// =head1 SEE ALSO
// avalon_st_source_bfm
// =cut
 
/ast_sink/altera_avalon_st_sink_bfm_171/sim/avalon_utilities_pkg.sv
0,0 → 1,80
// (C) 2001-2017 Intel Corporation. All rights reserved.
// Your use of Intel Corporation's design tools, logic functions and other
// software and tools, and its AMPP partner logic functions, and any output
// files from any of the foregoing (including device programming or simulation
// files), and any associated documentation or information are expressly subject
// to the terms and conditions of the Intel Program License Subscription
// Agreement, Intel FPGA IP License Agreement, or other applicable
// license agreement, including, without limitation, that your use is for the
// sole purpose of programming logic devices manufactured by Intel and sold by
// Intel or its authorized distributors. Please refer to the applicable
// agreement for further details.
 
 
// $Id: //acds/rel/17.1std/ip/sopc/components/verification/lib/avalon_utilities_pkg.sv#1 $
// $Revision: #1 $
// $Date: 2017/07/30 $
//-----------------------------------------------------------------------------
// =head1 NAME
// avalon_utilities_pkg
// =head1 SYNOPSIS
// Package for shared types and functions
//-----------------------------------------------------------------------------
// =head1 COPYRIGHT
// Copyright (c) 2008 Altera Corporation. All Rights Reserved.
// The information contained in this file is the property of Altera
// Corporation. Except as specifically authorized in writing by Altera
// Corporation, the holder of this file shall keep all information
// contained herein confidential and shall protect same in whole or in part
// from disclosure and dissemination to all third parties. Use of this
// program confirms your agreement with the terms of this license.
//-----------------------------------------------------------------------------
// =head1 DESCRIPTION
// This package contains shared types and functions.
// =cut
`timescale 1ns / 1ns
 
`ifndef _AVALON_UTILITIES_PKG_
`define _AVALON_UTILITIES_PKG_
 
package avalon_utilities_pkg;
 
function automatic int clog2(
bit [31:0] Depth
);
int i= Depth;
for(clog2 = 0; i > 0; clog2 = clog2 + 1)
i = i >> 1;
 
return clog2;
endfunction
 
function automatic int max(
bit [31:0] one,
bit [31:0] two
);
if(one > two)
return one;
else
return two;
endfunction
 
function automatic int lindex(
bit [31:0] width
);
// returns the left index for a vector having a declared width
// when width is 0, then the left index is set to 0 rather than -1
lindex = (width > 0) ? (width-1) : 0;
endfunction
typedef enum int {
LOW = 0,
HIGH = 1,
RANDOM = 2,
UNKNOWN = 3
} IdleOutputValue_t;
endpackage
 
`endif
/ast_sink/altera_avalon_st_sink_bfm_171/sim/verbosity_pkg.sv
0,0 → 1,193
// (C) 2001-2017 Intel Corporation. All rights reserved.
// Your use of Intel Corporation's design tools, logic functions and other
// software and tools, and its AMPP partner logic functions, and any output
// files from any of the foregoing (including device programming or simulation
// files), and any associated documentation or information are expressly subject
// to the terms and conditions of the Intel Program License Subscription
// Agreement, Intel FPGA IP License Agreement, or other applicable
// license agreement, including, without limitation, that your use is for the
// sole purpose of programming logic devices manufactured by Intel and sold by
// Intel or its authorized distributors. Please refer to the applicable
// agreement for further details.
 
 
// $Id: //acds/rel/17.1std/ip/sopc/components/verification/lib/verbosity_pkg.sv#1 $
// $Revision: #1 $
// $Date: 2017/07/30 $
//-----------------------------------------------------------------------------
// =head1 NAME
// verbosity_pkg
// =head1 SYNOPSIS
// Package for controlling verbosity of messages sent to the console
//-----------------------------------------------------------------------------
// =head1 COPYRIGHT
// Copyright (c) 2008 Altera Corporation. All Rights Reserved.
// The information contained in this file is the property of Altera
// Corporation. Except as specifically authorized in writing by Altera
// Corporation, the holder of this file shall keep all information
// contained herein confidential and shall protect same in whole or in part
// from disclosure and dissemination to all third parties. Use of this
// program confirms your agreement with the terms of this license.
//-----------------------------------------------------------------------------
// =head1 DESCRIPTION
// This module will dump diagnostic messages to the console during
// simulation. The level of verbosity can be controlled in the test
// bench by using the *set_verbosity* method in the imported package
// verbosity_pkg. For a given setting, message at that level and all
// lower levels are dumped. For example, setting VERBOSITY_DEBUG level
// causes all messages to be dumped, while VERBOSITY_FAILURE restricts
// only failure messages and those tagged as VERBOSITY_NONE to be
// dumped.
// The different levels are:
// =over 4
// =item 1 VERBOSITY_NONE
// Messages tagged with this level are always dumped to the console.
// =item 2 VERBOSITY_FAILURE
// A fatal simulation error has occurred and the simulator will exit.
// =item 3 VERBOSITY_ERROR
// A non-fatal error has occured. An example is a data comparison mismatch.
// =item 4 VERBOSITY_WARNING
// Warn the user that a potential error has occurred.
// =item 5 VERBOSITY_INFO
// Informational message.
// =item 6 VERBOSITY_DEBUG
// Dump enough state to diagnose problem scenarios.
// =back
 
 
`ifndef _AVALON_VERBOSITY_PKG_
`define _AVALON_VERBOSITY_PKG_
 
package verbosity_pkg;
 
timeunit 1ps;
timeprecision 1ps;
typedef enum int {VERBOSITY_NONE,
VERBOSITY_FAILURE,
VERBOSITY_ERROR,
VERBOSITY_WARNING,
VERBOSITY_INFO,
VERBOSITY_DEBUG} Verbosity_t;
 
Verbosity_t verbosity = VERBOSITY_INFO;
string message = "";
int dump_file;
int dump = 0;
 
//--------------------------------------------------------------------------
// =head1 Public Methods API
// =pod
// This section describes the public methods in the application programming
// interface (API). In this case the application program is the test bench
// or component which imports this package.
// =cut
//--------------------------------------------------------------------------
 
function automatic Verbosity_t get_verbosity(); // public
// Returns the global verbosity setting.
return verbosity;
endfunction
 
function automatic void set_verbosity ( // public
Verbosity_t v
);
// Sets the global verbosity setting.
 
string verbosity_str;
verbosity = v;
 
case(verbosity)
VERBOSITY_NONE: verbosity_str = "VERBOSITY_";
VERBOSITY_FAILURE: verbosity_str = "VERBOSITY_FAILURE";
VERBOSITY_ERROR: verbosity_str = "VERBOSITY_ERROR";
VERBOSITY_WARNING: verbosity_str = "VERBOSITY_WARNING";
VERBOSITY_INFO: verbosity_str = "VERBOSITY_INFO";
VERBOSITY_DEBUG: verbosity_str = "VERBOSITY_DEBUG";
default: verbosity_str = "UNKNOWN";
endcase
$sformat(message, "%m: Setting Verbosity level=%0d (%s)",
verbosity, verbosity_str);
print(VERBOSITY_NONE, message);
endfunction
 
function automatic void print( // public
Verbosity_t level,
string message
);
// Print a message to the console if the verbosity argument
// is less than or equal to the global verbosity setting.
string level_str;
 
if (level <= verbosity) begin
case(level)
VERBOSITY_NONE: level_str = "";
VERBOSITY_FAILURE: level_str = "FAILURE:";
VERBOSITY_ERROR: level_str = "ERROR:";
VERBOSITY_WARNING: level_str = "WARNING:";
VERBOSITY_INFO: level_str = "INFO:";
VERBOSITY_DEBUG: level_str = "DEBUG:";
default: level_str = "UNKNOWN:";
endcase
$display("%t: %s %s",$time, level_str, message);
if (dump) begin
$fdisplay(dump_file, "%t: %s %s",$time, level_str, message);
end
end
endfunction
 
function automatic void print_divider( // public
Verbosity_t level
);
// Prints a divider line to the console to make a block of related text
// easier to identify and read.
string message;
$sformat(message,
"------------------------------------------------------------");
print(level, message);
endfunction
function automatic void open_dump_file ( // public
string dump_file_name = "avalon_bfm_sim.log"
);
// Opens a dump file which collects console messages.
if (dump) begin
$sformat(message, "%m: Dump file already open - ignoring open.");
print(VERBOSITY_ERROR, message);
end else begin
dump_file = $fopen(dump_file_name, "w");
$fdisplay(dump_file, "testing dump file");
$sformat(message, "%m: Opening dump file: %s", dump_file_name);
print(VERBOSITY_INFO, message);
dump = 1;
end
endfunction
function automatic void close_dump_file(); // public
// Close the console message dump file.
if (!dump) begin
$sformat(message, "%m: No open dump file - ignoring close.");
print(VERBOSITY_ERROR, message);
end else begin
dump = 0;
$fclose(dump_file);
$sformat(message, "%m: Closing dump file");
print(VERBOSITY_INFO, message);
end
endfunction
 
function automatic void abort_simulation();
string message;
$sformat(message, "%m: Abort the simulation due to fatal error incident.");
print(VERBOSITY_FAILURE, message);
$stop;
endfunction
endpackage
// =cut
 
`endif
/ast_sink.qsys
0,0 → 1,91
<?xml version="1.0" encoding="UTF-8"?>
<system name="$${FILENAME}">
<component
name="$${FILENAME}"
displayName="$${FILENAME}"
version="1.0"
description=""
tags="INTERNAL_COMPONENT=true"
categories="" />
<parameter name="bonusData"><![CDATA[bonusData
{
element st_sink_bfm_0
{
datum _sortIndex
{
value = "0";
type = "int";
}
}
}
]]></parameter>
<parameter name="clockCrossingAdapter" value="HANDSHAKE" />
<parameter name="device" value="10AX115S2F45I1SG" />
<parameter name="deviceFamily" value="Arria 10" />
<parameter name="deviceSpeedGrade" value="1" />
<parameter name="fabricMode" value="QSYS" />
<parameter name="generateLegacySim" value="false" />
<parameter name="generationId" value="0" />
<parameter name="globalResetBus" value="false" />
<parameter name="hdlLanguage" value="VERILOG" />
<parameter name="hideFromIPCatalog" value="true" />
<parameter name="lockedInterfaceDefinition" value="" />
<parameter name="maxAdditionalLatency" value="1" />
<parameter name="projectName" value="" />
<parameter name="sopcBorderPoints" value="false" />
<parameter name="systemHash" value="0" />
<parameter name="testBenchDutName" value="" />
<parameter name="timeStamp" value="0" />
<parameter name="useTestBenchNamingPattern" value="false" />
<instanceScript></instanceScript>
<interface name="clk" internal="st_sink_bfm_0.clk" type="clock" dir="end">
<port name="clk" internal="clk" />
</interface>
<interface
name="clk_reset"
internal="st_sink_bfm_0.clk_reset"
type="reset"
dir="end">
<port name="reset" internal="reset" />
</interface>
<interface
name="sink"
internal="st_sink_bfm_0.sink"
type="avalon_streaming"
dir="end">
<port name="sink_data" internal="sink_data" />
<port name="sink_valid" internal="sink_valid" />
<port name="sink_ready" internal="sink_ready" />
<port name="sink_startofpacket" internal="sink_startofpacket" />
<port name="sink_endofpacket" internal="sink_endofpacket" />
<port name="sink_empty" internal="sink_empty" />
<port name="sink_channel" internal="sink_channel" />
<port name="sink_error" internal="sink_error" />
</interface>
<module
name="st_sink_bfm_0"
kind="altera_avalon_st_sink_bfm"
version="17.1"
enabled="1"
autoexport="1">
<parameter name="ST_BEATSPERCYCLE" value="1" />
<parameter name="ST_CHANNEL_W" value="2" />
<parameter name="ST_ERROR_DESCRIPTOR" value="" />
<parameter name="ST_ERROR_W" value="1" />
<parameter name="ST_MAX_CHANNELS" value="3" />
<parameter name="ST_NUMSYMBOLS" value="4" />
<parameter name="ST_READY_LATENCY" value="4" />
<parameter name="ST_SYMBOL_W" value="8" />
<parameter name="USE_CHANNEL" value="1" />
<parameter name="USE_EMPTY" value="1" />
<parameter name="USE_ERROR" value="1" />
<parameter name="USE_PACKET" value="1" />
<parameter name="USE_READY" value="1" />
<parameter name="USE_VALID" value="1" />
<parameter name="VHDL_ID" value="0" />
</module>
<interconnectRequirement for="$system" name="qsys_mm.clockCrossingAdapter" value="HANDSHAKE" />
<interconnectRequirement for="$system" name="qsys_mm.enableEccProtection" value="FALSE" />
<interconnectRequirement for="$system" name="qsys_mm.insertDefaultSlave" value="FALSE" />
<interconnectRequirement for="$system" name="qsys_mm.maxAdditionalLatency" value="1" />
</system>
/ast_source/altera_avalon_st_source_bfm_171/sim/altera_avalon_st_source_bfm.sv
0,0 → 1,908
// (C) 2001-2017 Intel Corporation. All rights reserved.
// Your use of Intel Corporation's design tools, logic functions and other
// software and tools, and its AMPP partner logic functions, and any output
// files from any of the foregoing (including device programming or simulation
// files), and any associated documentation or information are expressly subject
// to the terms and conditions of the Intel Program License Subscription
// Agreement, Intel FPGA IP License Agreement, or other applicable
// license agreement, including, without limitation, that your use is for the
// sole purpose of programming logic devices manufactured by Intel and sold by
// Intel or its authorized distributors. Please refer to the applicable
// agreement for further details.
 
 
// $File: //acds/rel/17.1std/ip/sopc/components/verification/altera_avalon_st_source_bfm/altera_avalon_st_source_bfm.sv $
// $Revision: #1 $
// $Date: 2017/07/30 $
// $Author: swbranch $
//-----------------------------------------------------------------------------
// =head1 NAME
// altera_avalon_st_source_bfm
// =head1 SYNOPSIS
// Bus Functional Model (BFM) for a Avalon Streaming Source
//-----------------------------------------------------------------------------
// =head1 DESCRIPTION
// This is a Bus Functional Model (BFM) for a Avalon Streaming Source.
// The behavior of each clock cycle of the ST protocol on the interface
// is governed by a transaction. Transactions are constructed using the
// the public API methods provided and are then pushed into a dispatch
// queue, either one at a time or as entire sequences. Response transactions
// are popped out of a separate response queue and inform the client of
// statistics such as back pressure latency.
//-----------------------------------------------------------------------------
`timescale 1ps / 1ps
 
module altera_avalon_st_source_bfm (
clk,
reset,
src_data,
src_channel,
src_valid,
src_startofpacket,
src_endofpacket,
src_error,
src_empty,
src_ready
);
 
// =head1 PARAMETERS
parameter ST_SYMBOL_W = 8; // Data symbol width in bits
parameter ST_NUMSYMBOLS = 4; // Number of symbols per word
parameter ST_CHANNEL_W = 0; // Channel width in bits
parameter ST_ERROR_W = 0; // Error width in bits
parameter ST_EMPTY_W = 0; // Empty width in bits
parameter ST_READY_LATENCY = 0; // Number of cycles latency after ready
parameter ST_MAX_CHANNELS = 1; // Maximum number of channels
parameter USE_PACKET = 0; // Use packet pins on interface
parameter USE_CHANNEL = 0; // Use channel pins on interface
parameter USE_ERROR = 0; // Use error pin on interface
parameter USE_READY = 1; // Use ready pin on interface
parameter USE_VALID = 1; // Use valid pin on interface
parameter USE_EMPTY = 0; // Use empty pin on interface
 
parameter ST_BEATSPERCYCLE = 1; // Max number of packets per cycle
parameter VHDL_ID = 0; // VHDL BFM ID number
 
localparam ST_DATA_W = ST_SYMBOL_W * ST_NUMSYMBOLS;
localparam ST_MDATA_W = ST_BEATSPERCYCLE * ST_DATA_W;
localparam ST_MCHANNEL_W = ST_BEATSPERCYCLE * ST_CHANNEL_W;
localparam ST_MERROR_W = ST_BEATSPERCYCLE * ST_ERROR_W;
localparam ST_MEMPTY_W = ST_BEATSPERCYCLE * ST_EMPTY_W;
// =head1 PINS
// =head2 Clock Interface
input clk;
input reset;
 
// =head2 Avalon Streaming Source Interface
output [lindex(ST_MDATA_W): 0] src_data;
output [lindex(ST_MCHANNEL_W): 0] src_channel;
output [ST_BEATSPERCYCLE-1: 0] src_valid;
output [ST_BEATSPERCYCLE-1: 0] src_startofpacket;
output [ST_BEATSPERCYCLE-1: 0] src_endofpacket;
output [lindex(ST_MERROR_W): 0] src_error;
output [lindex(ST_MEMPTY_W): 0] src_empty;
input src_ready;
 
// =cut
 
function int lindex;
// returns the left index for a vector having a declared width
// when width is 0, then the left index is set to 0 rather than -1
input [31:0] width;
lindex = (width > 0) ? (width-1) : 0;
endfunction
// synthesis translate_off
import verbosity_pkg::*;
import avalon_utilities_pkg::*;
typedef logic [lindex(ST_DATA_W) :0] STData_t;
typedef logic [lindex(ST_CHANNEL_W) :0] STChannel_t;
typedef logic [lindex(ST_EMPTY_W) :0] STEmpty_t;
typedef logic [lindex(ST_ERROR_W) :0] STError_t;
typedef logic [ST_BEATSPERCYCLE-1 :0] STBeats_t;
 
logic [ST_BEATSPERCYCLE-1 :0] src_valid;
logic [lindex(ST_MDATA_W) :0] src_data;
logic [lindex(ST_MCHANNEL_W) :0] src_channel;
logic [lindex(ST_MERROR_W) :0] src_error;
logic [lindex(ST_MEMPTY_W) :0] src_empty;
logic [ST_BEATSPERCYCLE-1 :0] src_startofpacket;
logic [ST_BEATSPERCYCLE-1 :0] src_endofpacket;
 
logic [ST_BEATSPERCYCLE-1 :0] src_valid_temp;
logic [lindex(ST_MDATA_W) :0] src_data_temp, src_data_slices;
logic [lindex(ST_MCHANNEL_W) :0] src_channel_temp, src_channel_slices;
logic [lindex(ST_MERROR_W) :0] src_error_temp, src_error_slices;
logic [lindex(ST_MEMPTY_W) :0] src_empty_temp, src_empty_slices;
logic [ST_BEATSPERCYCLE-1 :0] src_startofpacket_temp;
logic [ST_BEATSPERCYCLE-1 :0] src_endofpacket_temp;
//--------------------------------------------------------------------------
// Private Types and Variables
//--------------------------------------------------------------------------
typedef struct packed
{
bit [31:0] idles;
logic startofpacket;
logic endofpacket;
STChannel_t channel;
STData_t data;
STError_t error;
STEmpty_t empty;
bit valid;
} Transaction_t;
 
typedef struct packed
{
int latency;
int count;
} Response_t;
Transaction_t new_transaction;
Transaction_t current_transaction[ST_BEATSPERCYCLE];
Transaction_t transaction_queue[$];
 
Response_t current_response;
Response_t new_response;
Response_t response_queue[$];
int response_timeout = 100;
string message = "";
 
int idle_ctr = 0;
bit idle_state = 0;
int ready_latency_ctr = 0;
bit transaction_pending = 0;
int transaction_queue_size = 0;
int transaction_ctr = 0;
int max_transaction_queue_size = 256;
int min_transaction_queue_size = 2;
 
bit start = 0;
bit complete = 0;
 
logic src_ready_qualified;
logic src_is_now_ready;
logic load_transaction = 0;
STBeats_t src_valid_local;
IdleOutputValue_t idle_output_config = UNKNOWN;
localparam MAX_READY_DELAY = 8;
logic [MAX_READY_DELAY-1:0] src_ready_delayed;
 
//--------------------------------------------------------------------------
// Private Methods
//--------------------------------------------------------------------------
function int __floor(
int arg
);
// returns the arg if it is greater than 0, else returns 0
return (arg > 0) ? arg : 0;
endfunction
task __drive_temp_interface_idle();
case (idle_output_config)
LOW: begin
src_valid_temp <= 0;
src_startofpacket_temp <= '0;
src_endofpacket_temp <= '0;
src_channel_temp <= '0;
src_data_temp <= '0;
src_error_temp <= '0;
src_empty_temp <= '0;
end
HIGH: begin
src_valid_temp <= 0;
src_startofpacket_temp <= '1;
src_endofpacket_temp <= '1;
src_channel_temp <= '1;
src_data_temp <= '1;
src_error_temp <= '1;
src_empty_temp <= '1;
end
RANDOM: begin
src_valid_temp <= 0;
src_startofpacket_temp <= $random;
src_endofpacket_temp <= $random;
src_channel_temp <= $random;
src_data_temp <= $random;
src_error_temp <= $random;
src_empty_temp <= $random;
end
UNKNOWN: begin
src_valid_temp <= 0;
src_startofpacket_temp <= 'x;
src_endofpacket_temp <= 'x;
src_channel_temp <= 'x;
src_data_temp <= 'x;
src_error_temp <= 'x;
src_empty_temp <= 'x;
end
default: begin
src_valid_temp <= 0;
src_startofpacket_temp <= 'x;
src_endofpacket_temp <= 'x;
src_channel_temp <= 'x;
src_data_temp <= 'x;
src_error_temp <= 'x;
src_empty_temp <= 'x;
end
endcase
endtask
task __drive_interface_idle();
case (idle_output_config)
LOW: begin
src_valid = '0;
src_startofpacket = '0;
src_endofpacket = '0;
src_data = '0;
src_channel = '0;
src_error = '0;
src_empty = '0;
end
HIGH: begin
src_valid = '0;
src_startofpacket = '1;
src_endofpacket = '1;
src_data = '1;
src_channel = '1;
src_error = '1;
src_empty = '1;
end
RANDOM: begin
src_valid = '0;
src_startofpacket = $random;
src_endofpacket = $random;
src_data = $random;
src_channel = $random;
src_error = $random;
src_empty = $random;
end
UNKNOWN: begin
src_valid = '0;
src_startofpacket = 'x;
src_endofpacket = 'x;
src_data = 'x;
src_channel = 'x;
src_error = 'x;
src_empty = 'x;
end
default: begin
src_valid = '0;
src_startofpacket = 'x;
src_endofpacket = 'x;
src_data = 'x;
src_channel = 'x;
src_error = 'x;
src_empty = 'x;
end
endcase
endtask
 
function automatic void __hello();
// Introduction Message to console
$sformat(message, "%m: - Hello from altera_avalon_st_source_bfm.");
print(VERBOSITY_INFO, message);
$sformat(message, "%m: - $Revision: #1 $");
print(VERBOSITY_INFO, message);
$sformat(message, "%m: - $Date: 2017/07/30 $");
print(VERBOSITY_INFO, message);
$sformat(message, "%m: - ST_SYMBOL_W = %0d",
ST_SYMBOL_W);
print(VERBOSITY_INFO, message);
$sformat(message, "%m: - ST_NUMSYMBOLS = %0d",
ST_NUMSYMBOLS);
print(VERBOSITY_INFO, message);
$sformat(message, "%m: - ST_CHANNEL_W = %0d",
ST_CHANNEL_W);
print(VERBOSITY_INFO, message);
$sformat(message, "%m: - ST_ERROR_W = %0d",
ST_ERROR_W);
print(VERBOSITY_INFO, message);
$sformat(message, "%m: - ST_EMPTY_W = %0d",
ST_EMPTY_W);
print(VERBOSITY_INFO, message);
$sformat(message, "%m: - ST_READY_LATENCY = %0d",
ST_READY_LATENCY);
print(VERBOSITY_INFO, message);
$sformat(message, "%m: - ST_MAX_CHANNELS = %0d",
ST_MAX_CHANNELS);
print(VERBOSITY_INFO, message);
$sformat(message, "%m: - ST_BEATSPERCYCLE = %0d",
ST_BEATSPERCYCLE);
print(VERBOSITY_INFO, message);
$sformat(message, "%m: - USE_PACKET = %0d",
USE_PACKET);
print(VERBOSITY_INFO, message);
$sformat(message, "%m: - USE_CHANNEL = %0d",
USE_CHANNEL);
print(VERBOSITY_INFO, message);
$sformat(message, "%m: - USE_ERROR = %0d",
USE_ERROR);
print(VERBOSITY_INFO, message);
$sformat(message, "%m: - USE_READY = %0d",
USE_READY);
print(VERBOSITY_INFO, message);
$sformat(message, "%m: - USE_VALID = %0d",
USE_VALID);
print(VERBOSITY_INFO, message);
$sformat(message, "%m: - USE_EMPTY = %0d",
USE_EMPTY);
print(VERBOSITY_INFO, message);
print_divider(VERBOSITY_INFO);
endfunction
 
//--------------------------------------------------------------------------
// =head1 Public Methods API
// =pod
// This section describes the public methods in the application programming
// interface (API). In this case the application program is the test bench
// which instantiates and controls and queries state in this BFM component.
// Test programs must only use these public access methods and events to
// communicate with this BFM component. The API and the module pins
// are the only interfaces in this component that are guaranteed to be
// stable. The API will be maintained for the life of the product.
// While we cannot prevent a test program from directly accessing local
// tasks, functions, or data private to the BFM, there is no guarantee that
// these will be present in the future. In fact, it is best for the user
// to assume that the underlying implementation of this component can
// and will change.
// =cut
//--------------------------------------------------------------------------
event signal_fatal_error; // public
// Signal that a fatal error has occurred. Terminates simulation.
 
event signal_response_done; // public
// Signal
event signal_src_ready; // public
// Signal the assertion of the src_ready port.
 
event signal_src_not_ready; // public
// Signal the deassertion of the src_ready port implying sink backpressure
 
event signal_src_transaction_complete; // public
// Signal that all pending transactions have completed
 
event signal_src_transaction_almost_complete; // public
// Signal that BFM is driving the last pending transaction
event signal_src_driving_transaction; // public
// Signal that the source is driving the transaction onto the bus
 
event signal_max_transaction_queue_size; // public
// This event signals that the pending transaction queue size
// threshold has been exceeded
 
event signal_min_transaction_queue_size; // public
// This event signals that the pending transaction queue size
// is below the minimum threshold
function automatic string get_version(); // public
// Return BFM version string. For example, version 9.1 sp1 is "9.1sp1"
string ret_version = "17.1";
return ret_version;
endfunction
function automatic void set_idle_state_output_configuration( // public
// Set the configuration of output signal value during interface idle
IdleOutputValue_t output_config
);
$sformat(message, "%m: method called");
print(VERBOSITY_DEBUG, message);
idle_output_config = output_config;
endfunction
function automatic IdleOutputValue_t get_idle_state_output_configuration();
// Get the configuration of output signal value during interface idle
$sformat(message, "%m: method called");
print(VERBOSITY_DEBUG, message);
return idle_output_config;
endfunction
function automatic bit get_src_transaction_complete(); // public
// Return the transaction complete status
$sformat(message, "%m: called get_src_transaction_complete");
print(VERBOSITY_DEBUG, message);
return complete;
endfunction
 
function automatic logic get_src_ready(); // public
// Return the value of the src_ready port.
$sformat(message, "%m: called get_src_ready");
print(VERBOSITY_DEBUG, message);
return src_ready;
endfunction
 
function automatic void set_response_timeout( // public
int cycles = 100
);
// Set the number of cycles that may elapse during backpressure before
// the time out error is asserted. Disable the timeout by setting
// the cycles argument to zero.
response_timeout = cycles;
$sformat(message, "%m: called set_response_timeout");
print(VERBOSITY_DEBUG, message);
$sformat(message, "%m: Response timeout set to %0d cycles", response_timeout);
print(VERBOSITY_INFO, message);
endfunction
task automatic init(); // public
// Drive interface to idle state.
$sformat(message, "%m: called init");
print(VERBOSITY_DEBUG, message);
__drive_temp_interface_idle();
endtask
 
function automatic void push_transaction(); // public
// Push a new transaction into the local transaction queue.
// The BFM will drive the appropriate signals on the ST bus
// according to the transaction field values.
Transaction_t idle_transaction;
$sformat(message, "%m: called push_transaction");
print(VERBOSITY_DEBUG, message);
 
if (reset) begin
$sformat(message, "%m: Illegal command while reset asserted");
print(VERBOSITY_ERROR, message);
->signal_fatal_error;
end
// Idle cycles, defined as preceding the actual transaction are
// converted to an equal number of dummy transactions with the
// valid field set to 0. These are pushed into the queue before
// the actual transaction.
if (USE_VALID == 1) begin
idle_transaction.idles = 0;
idle_transaction.valid = 1'b0;
for (int i=0; i<new_transaction.idles; i++) begin
case (idle_output_config)
LOW: begin
idle_transaction.startofpacket = 1'b0;
idle_transaction.endofpacket = 1'b0;
idle_transaction.channel = '0;
idle_transaction.data = '0;
idle_transaction.error = '0;
idle_transaction.empty = '0;
end
HIGH: begin
idle_transaction.startofpacket = 1'b1;
idle_transaction.endofpacket = 1'b1;
idle_transaction.channel = '1;
idle_transaction.data = '1;
idle_transaction.error = '1;
idle_transaction.empty = '1;
end
RANDOM: begin
idle_transaction.startofpacket = $random;
idle_transaction.endofpacket = $random;
idle_transaction.channel = $random;
idle_transaction.data = $random;
idle_transaction.error = $random;
idle_transaction.empty = $random;
end
UNKNOWN: begin
idle_transaction.startofpacket = 1'bx;
idle_transaction.endofpacket = 1'bx;
idle_transaction.channel = 'x;
idle_transaction.data = 'x;
idle_transaction.error = 'x;
idle_transaction.empty = 'x;
end
default: begin
idle_transaction.startofpacket = 1'bx;
idle_transaction.endofpacket = 1'bx;
idle_transaction.channel = 'x;
idle_transaction.data = 'x;
idle_transaction.error = 'x;
idle_transaction.empty = 'x;
end
endcase
transaction_queue.push_back(idle_transaction);
end
end
// now push the actual valid transaction into the queue
new_transaction.idles = 0;
new_transaction.valid = 1;
transaction_queue.push_back(new_transaction);
endfunction
 
function automatic int get_transaction_queue_size(); // public
// Return the number of transactions in the local queues.
$sformat(message, "%m: called get_transaction_queue_size");
print(VERBOSITY_DEBUG, message);
return transaction_queue.size();
endfunction
 
function automatic int get_response_queue_size(); // public
// Return the number of transactions in the response queues.
$sformat(message, "%m: called get_response_queue_size");
print(VERBOSITY_DEBUG, message);
return response_queue.size();
endfunction
 
function automatic void set_transaction_data( // public
bit [ST_DATA_W-1:0] data
);
// Set the transaction data value
$sformat(message, "%m: called set_transaction_data - %h", data);
print(VERBOSITY_DEBUG, message);
new_transaction.data = data;
endfunction
 
function automatic void set_transaction_channel( // public
bit [ST_CHANNEL_W-1 :0] channel
);
// Set the transaction channel value
$sformat(message, "%m: called set_transaction_channel - %h", channel);
print(VERBOSITY_DEBUG, message);
new_transaction.channel = channel;
endfunction
 
function automatic void set_transaction_idles( // public
bit[31:0] idle_cycles
);
// Set the number of idle cycles to elapse before driving the
// transaction onto the Avalon bus.
if (USE_VALID > 0) begin
$sformat(message, "%m: called set_transaction_idles - %h",
idle_cycles);
print(VERBOSITY_DEBUG, message);
new_transaction.idles = idle_cycles;
end else begin
$sformat(message, "%m: Ignored. Idles set to 0 when USE_VALID == 0");
print(VERBOSITY_WARNING, message);
new_transaction.idles = 0;
end
endfunction
 
function automatic void set_transaction_sop( // public
bit sop
);
// Set the transaction start of packet value
$sformat(message, "%m: called set_transaction_sop - %b", sop);
print(VERBOSITY_DEBUG, message);
new_transaction.startofpacket = sop;
endfunction
 
function automatic void set_transaction_eop( // public
bit eop
);
// Set the transaction end of packet value
$sformat(message, "%m: called set_transaction_eop - %b", eop);
print(VERBOSITY_DEBUG, message);
new_transaction.endofpacket = eop;
endfunction
 
function automatic void set_transaction_error( // public
bit [ST_ERROR_W-1:0] error
);
// Set the transaction error value
$sformat(message, "%m: called set_transaction_error - %h", error);
print(VERBOSITY_DEBUG, message);
new_transaction.error = error;
endfunction
 
function automatic void set_transaction_empty( // public
bit [ST_EMPTY_W-1:0] empty
);
// Set the transaction empty value
$sformat(message, "%m: called set_transaction_empty - %h", empty);
print(VERBOSITY_DEBUG, message);
new_transaction.empty = empty;
endfunction
function automatic void pop_response(); // public
// Pop the response transaction from the queue before querying contents
string message;
 
$sformat(message, "%m: called pop_response - queue depth %0d",
response_queue.size());
print(VERBOSITY_DEBUG, message);
 
if (response_queue.size() == 0) begin
$sformat(message, "%m: Illegal command: response queue is empty");
print(VERBOSITY_ERROR, message);
->signal_fatal_error;
end
current_response = response_queue.pop_front();
endfunction
 
function automatic int get_response_latency(); // public
// Return the response latency due to back pressure for a
// transaction. The value is in terms of clock cycles.
$sformat(message, "%m: called get_response_latency - %0d",
current_response.latency);
print(VERBOSITY_DEBUG, message);
return current_response.latency;
endfunction
 
function automatic void set_max_transaction_queue_size( // public
int size
);
// Set the pending transaction maximum queue size threshold.
// The public event signal_max_transaction_queue_size
// will fire when the threshold is exceeded.
max_transaction_queue_size = size;
endfunction
 
function automatic void set_min_transaction_queue_size( // public
int size
);
// Set the pending transaction minimum queue size threshold.
// The public event signal_min_transaction_queue_size
// will fire when the queue level is below this threshold.
min_transaction_queue_size = size;
endfunction
//=cut
 
initial begin
__hello();
end
always @(posedge clk) begin
if (transaction_queue.size() > max_transaction_queue_size) begin
->signal_max_transaction_queue_size;
end else if (transaction_queue.size() < min_transaction_queue_size) begin
->signal_min_transaction_queue_size;
end
end
 
always @(signal_fatal_error) abort_simulation();
 
 
// The ST_BEATSPERCYCLE parameter complicates the driving of transactions
// somewhat as not all beats in a given cycle need to be valid.
// The following scenarios are possible:
// Transactions with no idle cycles:
// 1 There are an integral multiple of ST_BEATSPERCYCLE transactions
// in the pending transaction queue:
// All transactions fit neatly into an integral number of cycles
// with all beats valid and no resulting bubbles.
// 2 There are a non integral multiple of ST_BEATSPERCYCLE transactions
// in the pending transaction queue:
// The final pending transaction(s) in the queue need to be driven
// out with unused beats being marked as invalid i.e. there are one
// or more bubbles (invalid beats) at the end of the transaction
// sequence.
// A transaction with idle cycles defined is decomposed into a sequence of
// transactions. First there is a sequence of non valid, empty transaction
// beats which define the idle cycles or bubbles. And finally, there is
// one valid transaction beat.
 
// delay chain for src_ready back pressure input to account for latency
always @(posedge clk or posedge reset) begin
if (reset) begin
src_ready_delayed <= 0;
end else begin
src_ready_delayed <= {src_ready_delayed[6:0], src_ready};
end
end
assign src_ready_qualified = (USE_READY == 0)? 1'b1 :
(ST_READY_LATENCY == 0)? src_ready :
src_ready_delayed[__floor(ST_READY_LATENCY-1)];
assign src_is_now_ready = (USE_READY == 0)? 1'b1 :
(ST_READY_LATENCY <= 1)? src_ready :
src_ready_delayed[__floor(ST_READY_LATENCY-2)];
 
always @(*) begin
src_valid_local = src_valid_temp;
 
if (USE_VALID > 0) begin
if (USE_READY == 0 || ST_READY_LATENCY == 0) begin
src_valid = src_valid_temp;
src_startofpacket = src_startofpacket_temp;
src_endofpacket = src_endofpacket_temp;
src_data = src_data_temp;
src_channel = src_channel_temp;
src_error = src_error_temp;
src_empty = src_empty_temp;
end else begin
if (src_ready_qualified) begin
src_valid = src_valid_temp;
src_startofpacket = src_startofpacket_temp;
src_endofpacket = src_endofpacket_temp;
src_data = src_data_temp;
src_channel = src_channel_temp;
src_error = src_error_temp;
src_empty = src_empty_temp;
end else begin
__drive_interface_idle();
end
end
end else begin
src_valid = 0;
src_startofpacket = src_startofpacket_temp;
src_endofpacket = src_endofpacket_temp;
src_data = src_data_temp;
src_channel = src_channel_temp;
src_error = src_error_temp;
src_empty = src_empty_temp;
end
end
 
bit pending;
int response_transaction_ctr;
always @(posedge clk or posedge reset) begin
if (reset) begin
ready_latency_ctr <= 0;
complete <= 0;
response_transaction_ctr = 0;
new_response = 0;
current_response = 0;
response_queue = {};
end else begin
if (src_ready_qualified && ((src_valid != 0) || (USE_VALID == 0))) begin
ready_latency_ctr <= 0;
 
if (transaction_pending) begin
new_response.count = response_transaction_ctr++;
new_response.latency = ready_latency_ctr;
response_queue.push_back(new_response);
->signal_response_done;
end
 
end else begin
if (transaction_pending && ((src_valid != 0) || (USE_VALID == 0)))
ready_latency_ctr <= ready_latency_ctr + 1;
end
if ((get_transaction_queue_size() == 0) && src_ready_qualified &&
(USE_READY == 0 || src_valid != 0)) begin
complete <= 1;
->signal_src_transaction_complete;
end else if (complete &&
((get_transaction_queue_size() > 0) || transaction_pending)) begin
complete <= 0;
end
if ((response_timeout != 0) && (ready_latency_ctr > response_timeout)) begin
$sformat(message, "%m: Response Timeout");
print(VERBOSITY_FAILURE, message);
->signal_fatal_error;
end
end
end
 
always @(posedge clk or posedge reset) begin
if (reset) begin
idle_ctr <= 0;
transaction_pending = 0; // keep blocking
__drive_temp_interface_idle();
new_transaction = 0;
transaction_queue = {};
for (int i=0; i<ST_BEATSPERCYCLE; i++) begin
current_transaction[i] = 0;
end
end else begin
__drive_temp_interface_idle();
 
// reset transaction_pending after complete the current transsaction
if ((USE_READY == 0 || ST_READY_LATENCY == 0) &&
(src_ready_qualified || src_valid_local == 0)) begin
transaction_pending = 0;
end
if (USE_READY == 1 && ST_READY_LATENCY > 0 && src_ready_qualified == 1) begin
transaction_pending = 0;
end
if (~transaction_pending && get_transaction_queue_size() > 0) begin
transaction_pending = 1;
load_transaction = 1;
 
// initialize all beats to be invalid
for (int i=0; i<ST_BEATSPERCYCLE; i++)
current_transaction[i].valid = 0;
for (int i=0; i<ST_BEATSPERCYCLE; i++) begin
if (get_transaction_queue_size() == 0)
break;
current_transaction[i] = transaction_queue.pop_front();
end
end
if (transaction_pending) begin
if (idle_ctr == 0) begin
for (int i=0; i<ST_BEATSPERCYCLE; i++) begin
src_valid_temp[i] <=
current_transaction[i].valid;
src_startofpacket_temp[i] <=
current_transaction[i].startofpacket;
src_endofpacket_temp[i] <=
current_transaction[i].endofpacket;
end
// initialize slices immediately with non-blocking assigns
src_data_slices = '0;
src_channel_slices = '0;
src_error_slices = '0;
src_empty_slices = '0;
// each beat immediately assigned to interface port slice
for (int i=0; i<ST_BEATSPERCYCLE; i++) begin
src_data_slices = src_data_slices |
current_transaction[i].data << (i*ST_DATA_W);
src_channel_slices = src_channel_slices |
current_transaction[i].channel << (i*ST_CHANNEL_W);
src_error_slices = src_error_slices |
current_transaction[i].error << (i*ST_ERROR_W);
src_empty_slices = src_empty_slices |
current_transaction[i].empty << (i*ST_EMPTY_W);
end
// schedule final slice assignments
src_data_temp <= src_data_slices;
src_channel_temp <= src_channel_slices;
src_error_temp <= src_error_slices;
src_empty_temp <= src_empty_slices;
fork
begin
#0;
for (int i=0; i<ST_BEATSPERCYCLE; i++) begin
if (load_transaction && current_transaction[i].valid) begin
if (USE_READY == 0 || ST_READY_LATENCY == 0) begin
->signal_src_driving_transaction;
load_transaction = 0;
end else if (ST_READY_LATENCY > 0 && src_is_now_ready == 1) begin
->signal_src_driving_transaction;
load_transaction = 0;
end
end
end
end
join_none
end else begin
idle_ctr = idle_ctr - 1;
end
end
end
end
 
always@(signal_src_driving_transaction) begin
if (get_transaction_queue_size() == 0)
-> signal_src_transaction_almost_complete;
end
 
always @(posedge src_ready_qualified or negedge src_ready_qualified) begin
if (src_ready_qualified)
->signal_src_ready;
else
->signal_src_not_ready;
end
// synthesis translate_on
 
endmodule
 
// =head1 SEE ALSO
// avalon_st_sink_bfm
// =cut
 
 
 
 
 
 
 
 
/ast_source/altera_avalon_st_source_bfm_171/sim/avalon_utilities_pkg.sv
0,0 → 1,80
// (C) 2001-2017 Intel Corporation. All rights reserved.
// Your use of Intel Corporation's design tools, logic functions and other
// software and tools, and its AMPP partner logic functions, and any output
// files from any of the foregoing (including device programming or simulation
// files), and any associated documentation or information are expressly subject
// to the terms and conditions of the Intel Program License Subscription
// Agreement, Intel FPGA IP License Agreement, or other applicable
// license agreement, including, without limitation, that your use is for the
// sole purpose of programming logic devices manufactured by Intel and sold by
// Intel or its authorized distributors. Please refer to the applicable
// agreement for further details.
 
 
// $Id: //acds/rel/17.1std/ip/sopc/components/verification/lib/avalon_utilities_pkg.sv#1 $
// $Revision: #1 $
// $Date: 2017/07/30 $
//-----------------------------------------------------------------------------
// =head1 NAME
// avalon_utilities_pkg
// =head1 SYNOPSIS
// Package for shared types and functions
//-----------------------------------------------------------------------------
// =head1 COPYRIGHT
// Copyright (c) 2008 Altera Corporation. All Rights Reserved.
// The information contained in this file is the property of Altera
// Corporation. Except as specifically authorized in writing by Altera
// Corporation, the holder of this file shall keep all information
// contained herein confidential and shall protect same in whole or in part
// from disclosure and dissemination to all third parties. Use of this
// program confirms your agreement with the terms of this license.
//-----------------------------------------------------------------------------
// =head1 DESCRIPTION
// This package contains shared types and functions.
// =cut
`timescale 1ns / 1ns
 
`ifndef _AVALON_UTILITIES_PKG_
`define _AVALON_UTILITIES_PKG_
 
package avalon_utilities_pkg;
 
function automatic int clog2(
bit [31:0] Depth
);
int i= Depth;
for(clog2 = 0; i > 0; clog2 = clog2 + 1)
i = i >> 1;
 
return clog2;
endfunction
 
function automatic int max(
bit [31:0] one,
bit [31:0] two
);
if(one > two)
return one;
else
return two;
endfunction
 
function automatic int lindex(
bit [31:0] width
);
// returns the left index for a vector having a declared width
// when width is 0, then the left index is set to 0 rather than -1
lindex = (width > 0) ? (width-1) : 0;
endfunction
typedef enum int {
LOW = 0,
HIGH = 1,
RANDOM = 2,
UNKNOWN = 3
} IdleOutputValue_t;
endpackage
 
`endif
/ast_source/altera_avalon_st_source_bfm_171/sim/verbosity_pkg.sv
0,0 → 1,193
// (C) 2001-2017 Intel Corporation. All rights reserved.
// Your use of Intel Corporation's design tools, logic functions and other
// software and tools, and its AMPP partner logic functions, and any output
// files from any of the foregoing (including device programming or simulation
// files), and any associated documentation or information are expressly subject
// to the terms and conditions of the Intel Program License Subscription
// Agreement, Intel FPGA IP License Agreement, or other applicable
// license agreement, including, without limitation, that your use is for the
// sole purpose of programming logic devices manufactured by Intel and sold by
// Intel or its authorized distributors. Please refer to the applicable
// agreement for further details.
 
 
// $Id: //acds/rel/17.1std/ip/sopc/components/verification/lib/verbosity_pkg.sv#1 $
// $Revision: #1 $
// $Date: 2017/07/30 $
//-----------------------------------------------------------------------------
// =head1 NAME
// verbosity_pkg
// =head1 SYNOPSIS
// Package for controlling verbosity of messages sent to the console
//-----------------------------------------------------------------------------
// =head1 COPYRIGHT
// Copyright (c) 2008 Altera Corporation. All Rights Reserved.
// The information contained in this file is the property of Altera
// Corporation. Except as specifically authorized in writing by Altera
// Corporation, the holder of this file shall keep all information
// contained herein confidential and shall protect same in whole or in part
// from disclosure and dissemination to all third parties. Use of this
// program confirms your agreement with the terms of this license.
//-----------------------------------------------------------------------------
// =head1 DESCRIPTION
// This module will dump diagnostic messages to the console during
// simulation. The level of verbosity can be controlled in the test
// bench by using the *set_verbosity* method in the imported package
// verbosity_pkg. For a given setting, message at that level and all
// lower levels are dumped. For example, setting VERBOSITY_DEBUG level
// causes all messages to be dumped, while VERBOSITY_FAILURE restricts
// only failure messages and those tagged as VERBOSITY_NONE to be
// dumped.
// The different levels are:
// =over 4
// =item 1 VERBOSITY_NONE
// Messages tagged with this level are always dumped to the console.
// =item 2 VERBOSITY_FAILURE
// A fatal simulation error has occurred and the simulator will exit.
// =item 3 VERBOSITY_ERROR
// A non-fatal error has occured. An example is a data comparison mismatch.
// =item 4 VERBOSITY_WARNING
// Warn the user that a potential error has occurred.
// =item 5 VERBOSITY_INFO
// Informational message.
// =item 6 VERBOSITY_DEBUG
// Dump enough state to diagnose problem scenarios.
// =back
 
 
`ifndef _AVALON_VERBOSITY_PKG_
`define _AVALON_VERBOSITY_PKG_
 
package verbosity_pkg;
 
timeunit 1ps;
timeprecision 1ps;
typedef enum int {VERBOSITY_NONE,
VERBOSITY_FAILURE,
VERBOSITY_ERROR,
VERBOSITY_WARNING,
VERBOSITY_INFO,
VERBOSITY_DEBUG} Verbosity_t;
 
Verbosity_t verbosity = VERBOSITY_INFO;
string message = "";
int dump_file;
int dump = 0;
 
//--------------------------------------------------------------------------
// =head1 Public Methods API
// =pod
// This section describes the public methods in the application programming
// interface (API). In this case the application program is the test bench
// or component which imports this package.
// =cut
//--------------------------------------------------------------------------
 
function automatic Verbosity_t get_verbosity(); // public
// Returns the global verbosity setting.
return verbosity;
endfunction
 
function automatic void set_verbosity ( // public
Verbosity_t v
);
// Sets the global verbosity setting.
 
string verbosity_str;
verbosity = v;
 
case(verbosity)
VERBOSITY_NONE: verbosity_str = "VERBOSITY_";
VERBOSITY_FAILURE: verbosity_str = "VERBOSITY_FAILURE";
VERBOSITY_ERROR: verbosity_str = "VERBOSITY_ERROR";
VERBOSITY_WARNING: verbosity_str = "VERBOSITY_WARNING";
VERBOSITY_INFO: verbosity_str = "VERBOSITY_INFO";
VERBOSITY_DEBUG: verbosity_str = "VERBOSITY_DEBUG";
default: verbosity_str = "UNKNOWN";
endcase
$sformat(message, "%m: Setting Verbosity level=%0d (%s)",
verbosity, verbosity_str);
print(VERBOSITY_NONE, message);
endfunction
 
function automatic void print( // public
Verbosity_t level,
string message
);
// Print a message to the console if the verbosity argument
// is less than or equal to the global verbosity setting.
string level_str;
 
if (level <= verbosity) begin
case(level)
VERBOSITY_NONE: level_str = "";
VERBOSITY_FAILURE: level_str = "FAILURE:";
VERBOSITY_ERROR: level_str = "ERROR:";
VERBOSITY_WARNING: level_str = "WARNING:";
VERBOSITY_INFO: level_str = "INFO:";
VERBOSITY_DEBUG: level_str = "DEBUG:";
default: level_str = "UNKNOWN:";
endcase
$display("%t: %s %s",$time, level_str, message);
if (dump) begin
$fdisplay(dump_file, "%t: %s %s",$time, level_str, message);
end
end
endfunction
 
function automatic void print_divider( // public
Verbosity_t level
);
// Prints a divider line to the console to make a block of related text
// easier to identify and read.
string message;
$sformat(message,
"------------------------------------------------------------");
print(level, message);
endfunction
function automatic void open_dump_file ( // public
string dump_file_name = "avalon_bfm_sim.log"
);
// Opens a dump file which collects console messages.
if (dump) begin
$sformat(message, "%m: Dump file already open - ignoring open.");
print(VERBOSITY_ERROR, message);
end else begin
dump_file = $fopen(dump_file_name, "w");
$fdisplay(dump_file, "testing dump file");
$sformat(message, "%m: Opening dump file: %s", dump_file_name);
print(VERBOSITY_INFO, message);
dump = 1;
end
endfunction
function automatic void close_dump_file(); // public
// Close the console message dump file.
if (!dump) begin
$sformat(message, "%m: No open dump file - ignoring close.");
print(VERBOSITY_ERROR, message);
end else begin
dump = 0;
$fclose(dump_file);
$sformat(message, "%m: Closing dump file");
print(VERBOSITY_INFO, message);
end
endfunction
 
function automatic void abort_simulation();
string message;
$sformat(message, "%m: Abort the simulation due to fatal error incident.");
print(VERBOSITY_FAILURE, message);
$stop;
endfunction
endpackage
// =cut
 
`endif
/ast_source.qsys
0,0 → 1,91
<?xml version="1.0" encoding="UTF-8"?>
<system name="$${FILENAME}">
<component
name="$${FILENAME}"
displayName="$${FILENAME}"
version="1.0"
description=""
tags="INTERNAL_COMPONENT=true"
categories="" />
<parameter name="bonusData"><![CDATA[bonusData
{
element st_source_bfm_0
{
datum _sortIndex
{
value = "0";
type = "int";
}
}
}
]]></parameter>
<parameter name="clockCrossingAdapter" value="HANDSHAKE" />
<parameter name="device" value="10AX115S2F45I1SG" />
<parameter name="deviceFamily" value="Arria 10" />
<parameter name="deviceSpeedGrade" value="1" />
<parameter name="fabricMode" value="QSYS" />
<parameter name="generateLegacySim" value="false" />
<parameter name="generationId" value="0" />
<parameter name="globalResetBus" value="false" />
<parameter name="hdlLanguage" value="VERILOG" />
<parameter name="hideFromIPCatalog" value="true" />
<parameter name="lockedInterfaceDefinition" value="" />
<parameter name="maxAdditionalLatency" value="1" />
<parameter name="projectName" value="" />
<parameter name="sopcBorderPoints" value="false" />
<parameter name="systemHash" value="0" />
<parameter name="testBenchDutName" value="" />
<parameter name="timeStamp" value="0" />
<parameter name="useTestBenchNamingPattern" value="false" />
<instanceScript></instanceScript>
<interface name="clk" internal="st_source_bfm_0.clk" type="clock" dir="end">
<port name="clk" internal="clk" />
</interface>
<interface
name="clk_reset"
internal="st_source_bfm_0.clk_reset"
type="reset"
dir="end">
<port name="reset" internal="reset" />
</interface>
<interface
name="src"
internal="st_source_bfm_0.src"
type="avalon_streaming"
dir="start">
<port name="src_data" internal="src_data" />
<port name="src_valid" internal="src_valid" />
<port name="src_ready" internal="src_ready" />
<port name="src_startofpacket" internal="src_startofpacket" />
<port name="src_endofpacket" internal="src_endofpacket" />
<port name="src_empty" internal="src_empty" />
<port name="src_channel" internal="src_channel" />
<port name="src_error" internal="src_error" />
</interface>
<module
name="st_source_bfm_0"
kind="altera_avalon_st_source_bfm"
version="17.1"
enabled="1"
autoexport="1">
<parameter name="ST_BEATSPERCYCLE" value="1" />
<parameter name="ST_CHANNEL_W" value="2" />
<parameter name="ST_ERROR_DESCRIPTOR" value="" />
<parameter name="ST_ERROR_W" value="1" />
<parameter name="ST_MAX_CHANNELS" value="3" />
<parameter name="ST_NUMSYMBOLS" value="4" />
<parameter name="ST_READY_LATENCY" value="4" />
<parameter name="ST_SYMBOL_W" value="8" />
<parameter name="USE_CHANNEL" value="1" />
<parameter name="USE_EMPTY" value="1" />
<parameter name="USE_ERROR" value="1" />
<parameter name="USE_PACKET" value="1" />
<parameter name="USE_READY" value="1" />
<parameter name="USE_VALID" value="1" />
<parameter name="VHDL_ID" value="0" />
</module>
<interconnectRequirement for="$system" name="qsys_mm.clockCrossingAdapter" value="HANDSHAKE" />
<interconnectRequirement for="$system" name="qsys_mm.enableEccProtection" value="FALSE" />
<interconnectRequirement for="$system" name="qsys_mm.insertDefaultSlave" value="FALSE" />
<interconnectRequirement for="$system" name="qsys_mm.maxAdditionalLatency" value="1" />
</system>

powered by: WebSVN 2.1.0

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