- Software Control: The system is controlled through a software application running on an embedded Arm processor or external x86 processor, using drivers to access elements of the hardware design, and reading and writing registers in the hardware to control the execution of IP in the system.
- Self Synchronous: In this mode the IP exposes signals which are used for starting and stopping the kernel. These signals are driven by other IP or other elements of the system design that handles the execution of the IP.
The Vivado IP flow supports memory, stream, and register interface paradigms where each paradigm supports different interface protocols to communicate with the external world, as shown in the following table. Note that while the Vitis kernel flow supports only the AXI4 interface adapters, this flow supports a number of different interface types.
Paradigm | Description | Interface Types |
---|---|---|
Memory | Data is accessed by the kernel through memory such as DDR, HBM, PLRAM/BRAM/URAM |
ap_memory ,
bram , AXI4 Memory
Mapped (m_axi ) |
Stream | Data is streamed into the kernel from another streaming source, such as video processor or another kernel, and can also be streamed out of the kernel. |
ap_fifo , AXI4-Stream (axis ) |
Register | Data is accessed by the kernel through register interfaces performed by register reads and writes. |
ap_none , ap_hs , ap_ack ,
ap_ovld , ap_vld , and AXI4-Lite adapter
(s_axilite ). |
The default interfaces are defined by the C-argument type in the top-level function, and the default paradigm, as shown in the following table.
C-Argument Type | Supported Paradigms | Default Paradigm | Default Interface Protocol | ||
---|---|---|---|---|---|
Input | Output | Inout | |||
Scalar variable (pass by value) | Register | Register | ap_none | N/A | N/A |
Array | Memory, Stream | Memory | ap_memory | ap_memory | ap_memory |
Pointer | Memory, Stream, Register | Register | ap_none | ap_vld | ap_ovld |
Reference | Register | Register | ap_none | ap_vld | ap_vld |
hls::stream
|
Stream | Stream | ap_fifo | ap_fifo | N/A |
The default execution mode for Vivado
IP flow is sequential execution, which requires the HLS IP to complete one iteration before
starting the next. This is specified by the ap_ctrl_hs
block control protocol. The control protocol can be changed as specified in Block-Level Control Protocols.
The vadd
function in the following code
provides an example of interface synthesis in the Vivado IP flow.
#define VDATA_SIZE 16
typedef struct v_datatype { unsigned int data[VDATA_SIZE]; } v_dt;
extern "C" {
void vadd(const v_dt* in1, // Read-Only Vector 1
const v_dt* in2, // Read-Only Vector 2
v_dt* out_r, // Output Result for Addition
const unsigned int size // Size in integer
) {
unsigned int vSize = ((size - 1) / VDATA_SIZE) + 1;
// Auto-pipeline is going to apply pipeline to this loop
vadd1:
for (int i = 0; i < vSize; i++) {
vadd2:
for (int k = 0; k < VDATA_SIZE; k++) {
out_r[i].data[k] = in1[i].data[k] + in2[i].data[k];
}
}
}
}
The vadd
function includes:
- Two pointer inputs:
in1
andin2
- A pointer:
out_r
that the results are written to - A scalar value
size
With the default interface synthesis settings used for the Vivado IP flow, the design is synthesized into an RTL block with the ports and interfaces shown in the following figure.
In the default Vivado IP flow the tool creates three types of interface ports on the RTL design to handle the flow of both data and control.
- Clock and Reset ports:
ap_clk
andap_rst
are added to the kernel. - Block-level control protocol: The
ap_ctrl
interface is implemented as ans_axilite
interface. - Port-level interface protocols: These are created for each argument in
the top-level function and the function return (if the function returns a value). As
explained in the table above most of the arguments use a port protocol of
ap_none
, and so have no control signals. In thevadd
example above these ports include:in1
,in2
, andsize
. However, theout_r_o
output port uses theap_vld
protocol and so is associated with theout_r_o_ap_vld
signal.
AP_Memory in the Vivado IP Flow
The ap_memory
is the default
interface for the memory paradigm described in the tables above. In the Vivado IP flow it is used for communicating with memory
resources such as BRAM and URAM. The ap_memory
protocol also follows the address and data phase. The protocol initially requests to
read/write the resource and waits until it receives an acknowledgment of the resource
availability. It then initiates the data transfer phase of read/write.
An important consideration for ap_memory
is that it can only perform a single beat data transfer to a
single address, which is different from m_axi
which
can do burst accesses. This makes the ap_memory
a
lightweight protocol, compared to the others.
- Memory Resources: By default Vitis HLS implements a protocol to communicate with a single-port RAM
resource. You can control the implementation of the protocol by specifying the
storage_type
as part of the INTERFACE pragma or directive. Thestorage_type
lets you explicitly define which type of RAM is used, and which RAM ports are created (single-port or dual-port). If nostorage_type
is specified Vitis HLS uses:- A single-port RAM by default.
- A dual-port RAM if it reduces the initiation interval or latency.
M_AXI Interfaces in the Vivado IP Flow
m_axi
) interfaces allow an IP to read and write data in
global memory (DDR, HBM, PLRAM), Memory-mapped interfaces are a convenient way of
sharing data across multiple IP. The main advantages for m_axi
interfaces are listed below: - The interface has independent read and write channels
- It supports burst-based accesses
- It provides a queue for outstanding transactions
- Understanding Burst Access
-
AXI4 memory-mapped
interfaces support high throughput bursts of up to 4K bytes with just a single
address phase. With burst mode transfers, Vitis HLS reads or writes data using a single base address followed
by multiple sequential data samples, which makes this mode capable of higher data
throughput. Burst mode of operation is possible when you use the C
memcpy
function or a pipelinedfor
loop. Refer to Controlling AXI4 Burst Behavior or AXI Burst Transfers for more information. - Automatic Port Widening and Port Width Alignment
-
As discussed in Automatic Port Width Resizing, Vitis HLS has the ability to automatically widen a port width to facilitate data transfers and improve burst access when all the preconditions needed for bursting are present. In the Vivado IP flow the following configuration settings disable automatic port width resizing by default. To enable this feature you must change these configuration options (notice that one command is specified as bits and the other is specified as bytes):
config_interface -m_axi_max_widen_bitwidth 0 config_interface -m_axi_alignment_byte_size 0
- Specifying Alignment for Vivado IP mode
-
The alignment for an
m_axi
port allows the port to read and write memory according to the specified alignment. Choosing the correct alignment is important as it will impact performance in the best case, and can impact functionality in the worst case.Aligned memory access means that the pointer (or the start address of the data) is a multiple of a type-specific value called the alignment. The alignment is the natural address multiple where the type must be or should be stored (e.g. for performance reasons) on a Memory. For example, standard 32-bit architecture stores words of 32 bits, each of 4 bytes in the memory. The data is aligned to one-word or 4-byte boundary.
The alignment should be consistent in the system. The alignment is determined when the IP is operating in AXI4 master mode and should be specified, like the 32-bit architecture with 4-byte alignment. When the IP is operating in slave mode the alignment should match the alignment of the master.
- Rules for Offset
-
The default for
m_axi
offset is offset=direct and default_slave_interface=s_axilite. However, in the Vivado IP flow you can change it as described in Offset and Modes of Operation. - Bundle Interfaces - Performance vs. Resource Utilization
-
By default, Vitis HLS groups function arguments with compatible options into a single
m_axi
interface adapter as described in M_AXI Bundles. Bundling ports into a single interface helps save device resources by eliminating AXI4 logic, which can be necessary when working in congested designs.However, a single interface bundle can limit the performance of the IP because all the memory transfers have to go through a single interface. The
m_axi
interface has independent READ and WRITE channels, so a single interface can read and write simultaneously, though only at one location. Using multiple bundles lets you increase performance by creating multiple interfaces to connect to memory banks.
S_AXILITE in the Vivado IP Flow
In the Vivado IP flow, the default
execution control is managed by register reads and writes through an s_axilite
interface using the default ap_ctrl_hs
control protocol. The IP is software controlled
by reading and writing the control registers of an s_axilite
interface as described in S_AXILITE Control Register Map.
The s_axilite
interface provides the
following features:
- Control Protocols
- The block control protocol as specified in Block-Level Control Protocols.
- Scalar Arguments
- Scalar arguments from the top-level function can be mapped to an
s_axilite
interface which creates a register for the value as described in S_AXILITE Control Register Map. The software can perform reads/writes to this register space. - Rules for Offset
- The Vivado IP flow defines the size, or range of addresses assigned to a port based on the data type of the associated C-argument in the top-level function. However, the tool also lets you manually define the offset size as described in S_AXILITE Offset Option.
- Rules for Bundle
- In the Vivado IP flow you
can specify multiple bundles using the
s_axilite
interface, and this will create a separate interface adapter for each bundle you have defined. However, there are some rules related to using multiple bundles that you should be familiar with as explained in S_AXILITE Bundle Rules.
AP_FIFO in the Vivado IP Flow
In the Vivado IP flow, the ap_fifo
interface protocol is the default interface for the
streaming paradigm on the interface for communication with a memory resource FIFO, and
can also be used as a communication channel between different functions inside the IP.
This protocol should only be used if the data is accessed sequentially, and AMD
strongly recommends using the hls::stream<data type>
which implements a FIFO.
<data type>
should not be the same as the T_data_type
, which should only be used on the interface.
AXIS Interfaces in the Vivado IP Flow
The AXI4-Stream protocol (axis
) is an alternative for streaming interfaces, and
defines a single uni-directional channel for streaming data in a sequential
manner. Unlike the m_axi
protocol, the AXI4-Stream interfaces can burst an unlimited amount of
data, which significantly improves performance. Unlike the AXI4 memory-mapped interface which needs an address to read/write the
memory, the axis
interface simply passes data to
another axis
interface without needing an address, and
so uses fewer device resources. Combined, these features make the streaming interface a
light-weight high performance interface as described in AXI4-Stream Interfaces.