Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

axi_dmac: Delay input packet until IRQ is acknowledged #1486

Open
wants to merge 6 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
12 changes: 12 additions & 0 deletions docs/library/axi_dmac/index.rst
Original file line number Diff line number Diff line change
Expand Up @@ -140,6 +140,8 @@ Configuration Parameters
* - ENABLE_DIAGNOSTICS_IF
- Add insight into internal operation of the core, for debug purposes
only.
* - SG_DELAYED_INPUT
- Read one set of data at a time to prevent IRQ overlap for partial transfers.

Interface
--------------------------------------------------------------------------------
Expand Down Expand Up @@ -771,6 +773,16 @@ Scatter-Gather Datapath Width
The scatter-gather dedicated interface ``m_sg_axi`` currently supports only
64-bit transfers. ``DMA_DATA_WIDTH_SG`` can only be set to 64.

Scatter-Gather Delayed Input
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^

If the ``SG_DELAYED_INPUT`` HDL synthesis configuration parameter is set, the
DMA is set to accept one packet on the input interface and wait for the
interrupt to be acknowledged. This feature was specifically created for cases
where ``PARTIAL_REPORTING_EN`` is enabled. In these cases multiple interrupts
are not overlapping if multiple packets arrive before the previous IRQ is
acknowledged. This enables the user to process each interrupt request seprately.

Software Support
--------------------------------------------------------------------------------

Expand Down
4 changes: 2 additions & 2 deletions docs/regmap/adi_regmap_dmac.txt
Original file line number Diff line number Diff line change
Expand Up @@ -19,13 +19,13 @@ RO
ENDFIELD

FIELD
[15:8] 0x00000005
[15:8] 0x00000006
VERSION_MINOR
RO
ENDFIELD

FIELD
[7:0] 0x00000063
[7:0] 0x00000000
VERSION_PATCH
RO
ENDFIELD
Expand Down
8 changes: 6 additions & 2 deletions library/axi_dmac/axi_dmac.v
Original file line number Diff line number Diff line change
Expand Up @@ -73,7 +73,8 @@ module axi_dmac #(
parameter ALLOW_ASYM_MEM = 0,
parameter CACHE_COHERENT = 0,
parameter [3:0] AXI_AXCACHE = 4'b0011,
parameter [2:0] AXI_AXPROT = 3'b000
parameter [2:0] AXI_AXPROT = 3'b000,
parameter SG_DELAYED_INPUT = 0
) (

// Slave AXI interface
Expand Down Expand Up @@ -546,7 +547,8 @@ module axi_dmac #(
.ENABLE_DIAGNOSTICS_IF(ENABLE_DIAGNOSTICS_IF),
.ALLOW_ASYM_MEM(ALLOW_ASYM_MEM),
.AXI_AXCACHE(AXI_AXCACHE),
.AXI_AXPROT(AXI_AXPROT)
.AXI_AXPROT(AXI_AXPROT),
.SG_DELAYED_INPUT(SG_DELAYED_INPUT)
) i_transfer (
.ctrl_clk(s_axi_aclk),
.ctrl_resetn(s_axi_aresetn),
Expand All @@ -555,6 +557,8 @@ module axi_dmac #(
.ctrl_pause(ctrl_pause),
.ctrl_hwdesc(ctrl_hwdesc),

.irq(irq),

.req_valid(up_dma_req_valid),
.req_ready(up_dma_req_ready),
.req_dest_address(up_dma_req_dest_address),
Expand Down
7 changes: 7 additions & 0 deletions library/axi_dmac/axi_dmac_constr.ttcl
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@
<: set async_src_sg [getBooleanValue "ASYNC_CLK_SRC_SG"] :>
<: set async_dest_sg [getBooleanValue "ASYNC_CLK_DEST_SG"] :>
<: set sg_enabled [getBooleanValue "DMA_SG_TRANSFER"] :>
<: set sg_delayed_input [getBooleanValue "SG_DELAYED_INPUT"] :>
<: set disable_debug_registers [getBooleanValue "DISABLE_DEBUG_REGISTERS"] :>

set req_clk_ports_base {s_axi_aclk}
Expand Down Expand Up @@ -287,6 +288,12 @@ set_false_path \
set_false_path \
-to [get_pins -hierarchical * -filter {NAME=~*i_raddr_sync_gray/cdc_sync_stage1_reg[*]/D}]

<: if {$async_req_sg && $sg_delayed_input} { :>
set_max_delay -datapath_only \
-from [get_clocks -of_objects [get_ports $req_clk_ports_base]] \
-to [get_cells -hier -filter {NAME =~ *sync_bits_irq/cdc_sync_stage1_reg* && IS_SEQUENTIAL}] \
[get_property -min PERIOD [get_clocks -of_objects [get_ports $req_clk_ports_base]]]
<: } :>
<: } :>
# Reset signals
set_false_path -quiet \
Expand Down
33 changes: 28 additions & 5 deletions library/axi_dmac/axi_dmac_ip.tcl
Original file line number Diff line number Diff line change
Expand Up @@ -281,6 +281,7 @@ foreach {k v} { \
"DISABLE_DEBUG_REGISTERS" "false" \
"ENABLE_DIAGNOSTICS_IF" "false" \
"CACHE_COHERENT" "false" \
"SG_DELAYED_INPUT" "false" \
} { \
set_property -dict [list \
"value_format" "bool" \
Expand Down Expand Up @@ -454,24 +455,38 @@ set_property -dict [list \

set p [ipgui::get_guiparamspec -name "DMA_SG_TRANSFER" -component $cc]
ipgui::move_param -component $cc -order 1 $p -parent $feature_group
set_property -dict [list \
"tooltip" "Scatter-Gather Transfer Support" \
] $p
set_property -dict [list \
"display_name" "SG Transfer Support" \
"enablement_tcl_expr" "\$DMA_TYPE_SRC == 0 || \$DMA_TYPE_DEST == 0" \
] [ipx::get_user_parameters DMA_SG_TRANSFER -of_objects $cc]

set p [ipgui::get_guiparamspec -name "SG_DELAYED_INPUT" -component $cc]
ipgui::move_param -component $cc -order 2 $p -parent $feature_group
set_property -dict [list \
"tooltip" "Read one set of data at a time to prevent IRQ overlap for partial transfers" \
] $p
set_property -dict [list \
"display_name" "SG Slow Transfer Support" \
"enablement_tcl_expr" "\$DMA_SG_TRANSFER == true" \
] [ipx::get_user_parameters SG_DELAYED_INPUT -of_objects $cc]

set p [ipgui::get_guiparamspec -name "DMA_2D_TRANSFER" -component $cc]
ipgui::move_param -component $cc -order 2 $p -parent $feature_group
ipgui::move_param -component $cc -order 3 $p -parent $feature_group
set_property -dict [list \
"display_name" "2D Transfer Support" \
] $p

set p [ipgui::get_guiparamspec -name "SYNC_TRANSFER_START" -component $cc]
ipgui::move_param -component $cc -order 3 $p -parent $feature_group
ipgui::move_param -component $cc -order 4 $p -parent $feature_group
set_property -dict [list \
"display_name" "Transfer Start Synchronization Support" \
] $p

set p [ipgui::get_guiparamspec -name "CACHE_COHERENT" -component $cc]
ipgui::move_param -component $cc -order 4 $p -parent $feature_group
ipgui::move_param -component $cc -order 5 $p -parent $feature_group
set_property -dict [list \
"tooltip" "Assume DMA ports ensure cache coherence (e.g. Ultrascale HPC port)" \
] $p
Expand Down Expand Up @@ -510,14 +525,22 @@ set_property -dict [list \
set p [ipgui::get_guiparamspec -name "ASYNC_CLK_SRC_SG" -component $cc]
ipgui::move_param -component $cc -order 4 $p -parent $clk_group
set_property -dict [list \
"display_name" "Source and Scatter-Gather Clock Asynchronous" \
"tooltip" "Source and Scatter-Gather Clock Asynchronous" \
] $p
set_property -dict [list \
"display_name" "Source and Scatter-Gather Clock Asynchronous" \
"enablement_tcl_expr" "\$DMA_SG_TRANSFER == true" \
] [ipx::get_user_parameters ASYNC_CLK_SRC_SG -of_objects $cc]

set p [ipgui::get_guiparamspec -name "ASYNC_CLK_DEST_SG" -component $cc]
ipgui::move_param -component $cc -order 5 $p -parent $clk_group
set_property -dict [list \
"display_name" "Destination and Scatter-Gather Clock Asynchronous" \
"tooltip" "Destination and Scatter-Gather Clock Asynchronous" \
] $p
set_property -dict [list \
"display_name" "Destination and Scatter-Gather Clock Asynchronous" \
"enablement_tcl_expr" "\$DMA_SG_TRANSFER == true" \
] [ipx::get_user_parameters ASYNC_CLK_DEST_SG -of_objects $cc]

set dbg_group [ipgui::add_group -name {Debug} -component $cc \
-parent $page0 -display_name {Debug}]
Expand Down
2 changes: 2 additions & 0 deletions library/axi_dmac/axi_dmac_pkg_sv.ttcl
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,7 @@
<: set disable_debug_registers [get_property MODELPARAM_VALUE.DISABLE_DEBUG_REGISTERS] :>
<: set enable_diagnostics_if [get_property MODELPARAM_VALUE.ENABLE_DIAGNOSTICS_IF] :>
<: set cache_coherent [get_property MODELPARAM_VALUE.CACHE_COHERENT] :>
<: set sg_delayed_input [get_property MODELPARAM_VALUE.SG_DELAYED_INPUT] :>

<: proc b2i {b} { if {$b==true} {return 1} else {return 0}} :>
///////////////////////////////////////////////////////////////////////////
Expand Down Expand Up @@ -84,6 +85,7 @@ package <=: ComponentName :>_pkg;
parameter <=: ComponentName :>_DISABLE_DEBUG_REGISTERS = <=: b2i $disable_debug_registers :>;
parameter <=: ComponentName :>_ENABLE_DIAGNOSTICS_IF = <=: b2i $enable_diagnostics_if :>;
parameter <=: ComponentName :>_CACHE_COHERENT = <=: b2i $cache_coherent :>;
parameter <=: ComponentName :>_SG_DELAYED_INPUT = <=: b2i $sg_delayed_input :>;
//////////////////////////////////////////////////////////////////////////

endpackage : <=: ComponentName :>_pkg
2 changes: 1 addition & 1 deletion library/axi_dmac/axi_dmac_regmap.v
Original file line number Diff line number Diff line change
Expand Up @@ -123,7 +123,7 @@ module axi_dmac_regmap #(
input [31:0] dbg_ids1
);

localparam PCORE_VERSION = 'h00040563;
localparam PCORE_VERSION = 'h00040600;
localparam HAS_ADDR_HIGH = DMA_AXI_ADDR_WIDTH > 32;
localparam ADDR_LOW_MSB = HAS_ADDR_HIGH ? 31 : DMA_AXI_ADDR_WIDTH-1;

Expand Down
49 changes: 46 additions & 3 deletions library/axi_dmac/axi_dmac_transfer.v
Original file line number Diff line number Diff line change
Expand Up @@ -66,7 +66,8 @@ module axi_dmac_transfer #(
parameter ENABLE_DIAGNOSTICS_IF = 0,
parameter ALLOW_ASYM_MEM = 0,
parameter [3:0] AXI_AXCACHE = 4'b0011,
parameter [2:0] AXI_AXPROT = 3'b000
parameter [2:0] AXI_AXPROT = 3'b000,
parameter SG_DELAYED_INPUT = 0
) (
input ctrl_clk,
input ctrl_resetn,
Expand All @@ -75,6 +76,8 @@ module axi_dmac_transfer #(
input ctrl_pause,
input ctrl_hwdesc,

input irq,

input req_valid,
output req_ready,

Expand Down Expand Up @@ -261,6 +264,9 @@ module axi_dmac_transfer #(
wire abort_req;
wire dma_eot;

wire s_axis_ready_t;
wire s_axis_valid_t;

axi_dmac_reset_manager #(
.ASYNC_CLK_REQ_SRC (ASYNC_CLK_REQ_SRC),
.ASYNC_CLK_SRC_DEST (ASYNC_CLK_SRC_DEST),
Expand Down Expand Up @@ -312,6 +318,43 @@ module axi_dmac_transfer #(
assign req_sg_desc_id = ctrl_hwdesc ? dma_sg_hwdesc_id : 'h00;
assign dma_sg_in_req_valid = ctrl_hwdesc ? req_valid_gated : 1'b0;

generate if ((DMA_SG_TRANSFER == 1) && (SG_DELAYED_INPUT == 1)) begin

wire irq_cdc;
reg irq_d = 1'b0;
reg packet_received = 1'b0;

sync_bits #(
.NUM_OF_BITS (1),
.ASYNC_CLK (1)
) sync_bits_irq (
.in_bits (irq),
.out_clk (s_axis_aclk),
.out_resetn (1'b1),
.out_bits (irq_cdc));

always @(posedge s_axis_aclk) begin
irq_d <= irq_cdc;
end

always @(posedge s_axis_aclk) begin
if (s_axis_last && s_axis_valid && s_axis_ready)
packet_received <= 1'b1;
else
if (!irq_cdc && irq_d)
packet_received <= 1'b0;
end

assign s_axis_ready = (packet_received) ? 1'b0 : s_axis_ready_t;
assign s_axis_valid_t = (packet_received) ? 1'b0 : s_axis_valid;

end else begin

assign s_axis_ready = s_axis_ready_t;
assign s_axis_valid_t = s_axis_valid;

end endgenerate

/* SG Interface */
generate if (DMA_SG_TRANSFER == 1) begin

Expand Down Expand Up @@ -582,8 +625,8 @@ module axi_dmac_transfer #(
.m_axi_rresp (m_axi_rresp),

.s_axis_aclk (s_axis_aclk),
.s_axis_ready (s_axis_ready),
.s_axis_valid (s_axis_valid),
.s_axis_ready (s_axis_ready_t),
.s_axis_valid (s_axis_valid_t),
.s_axis_data (s_axis_data),
.s_axis_user (s_axis_user),
.s_axis_last (s_axis_last),
Expand Down
Loading