이전 글 목록
[HW] - Xilinx HLS tutorial (1) - VIVADO install & Tutorial Data Download
[HW] - Xilinx HLS tutorial (2) - Creating HLS project
[HW] - Xilinx HLS tutorial (3) - Tcl Command Interface 사용하기
[HW] - Xilinx HLS tutorial (4) - Port 설정
[HW] - [Xilinx] hls::Mat 사용에 대해서 // HLS convolution tutorial 이해를 위해
오늘은 HLS interface에 대한 내용을
온라인에 나와있는걸 마음대로 해석하여
적어보도록 하겠습니다.
두가지를 참조하여 적습니다.
1.
https://www.xilinx.com/html_docs/xilinx2017_4/sdaccel_doc/jit1504034365862.html
pragma HLS interface
Description In C based design, all input and output operations are performed, in zero time, through formal function arguments. In an RTL design these same input and output operations must be performed through a port in the design interface and typically op
www.xilinx.com
2. ug902 - Vivado-HLS
제 영어실력 때문에 제대로
전달되지 않을 가능성이 높으니
확실하게 하고 싶으신 분들은
꼭 문서를 직접 보시기 바랍니다.
C 기반의 설계에서 모든 입력과 출력 동작은
formal funciton argument들을 통해
동시에 수행됩니다.
RTL 설계에서 같은 입출력 동작은 반드시
design interface의 port를 통해서 수행되고
명확한 I/O protocol을 사용하여 동작합니다.
Vivado HLS는 C/C++을 이용해서 설계를 합니다.
사용되는 I/O protocol을 명확하게 하기위해서
Interface Synthesis를 수행합니다.
Interface Synthesis
top-level function이 합성될 때,
함수의 arguments(or parameters)는
RTL ports로 합성됩니다.
이 과정을 Interface Synthesis라고 부릅니다.
// Vivado HLS interface Synthesis Example Code
#include "sum_io.h"
dout_t sum_io(din_t in1, din_t in2, dio_t *sum) {
dout_t temp;
*sum = in1 + in2 + *sum;
temp = in1 + in2;
return temp;
}
위 코드는 ug902문서에 있는 코드입니다.
코드를 보면
in1, in2라는 두개의 input value가 있고
sum이라는 pointer 형태의
read, write 모두 수행하는 value가 있고
함수의 return을 통해
temp가 반환되도록 되어 있습니다.
Default interface synthesis setting으로
합성을 진행하게 되면
RTL Block의 port는
아래 그림과 같이 나타나게 됩니다.
위 그림에서 볼수 있는 것은
3가지 type의 Port가 있다는 것인데요
1. Clock and Reset port
ap_clk과 ap_rst 를 가지고 있습니다.
2. Block-Level interface protocol
ap_ctrl 이란 이름으로
ap_start
ap_done
ap_ready
ap_idle를 가지고 있습니다.
3. Port-Level interface protocol
top-level function의
각 argument와 function의 return에 의해
생성됩니다.
in1,
in2,
sum_i,
sum_o,
sum_o_ap_vld,
ap_return
등에 해당합니다.
이렇게 3가지 type은
각각 어떤 특징을 가지고 있는지
살펴 보겠습니다.
1. Clock and Reset Port
Design이 수행할 동작을 완료하기 위해서
1 cycle 이상이 필요하다면
A chip-enable는 전체 block에
선택적으로 추가 될 수 있습니다.
설정은 Solution-> Solution Setting ->General에서
config-interface configuration을
사용하면 된다고 하네요
reset동작은 config_rtl configuration을 통해서
사용가능하다고 합니다.
2. Block-Level Interface Protocol
설계에 block-level interface protocol은
default로 추가됩니다.
이 signal은 어떤 port-level의 I/O protocol들과
무관하게(독립적으로) block을 컨트롤 합니다.
이 포트는 block 여러개의 ports를 가지고 있는데
각각 동작하는 순간들이 정해져 있습니다.
ap_start :
block이 processing data를 시작할 수 있을 때
ap_ready :
새로운 input을 받을 준비가 되어 있을때
ap_idle :
idle 상태일 때
ap_done :
동작이 완료 되었을 때
위 4가지 상황에서 동작합니다.
3. Port-Level Interface Protocol
마지막 신호 그룹은 data ports 입니다.
I/O protocol은 C argument의
type에 따라 생성됩니다.
block-Level protocol을 이용하여
작업을 수행한 직후에
Port-level I/O protocols은 block 밖으로
데이터를 내보낼때 사용합니다
Default input pass-by-value
arguments and pointer는
handshaking signal 없이 데이터가 전달 됩니다.
그래서 위 코드예제에서 input port들은
I/O protocol이 없이
data port만을 사용해서 전달됩니다.
port가 지금 처럼 I/O protocol이 없는 경우에는
input data가 read 될때까지
반드시 안정적으로 유지되어야 합니다.
Default output pointer들은
output valid signal과 함께 구성되는데
valid signal은 output data가 유효함을 나타냅니다.
위 예제코드에서 output port는
sum_o_ap_vld 라고 명명된
output valid port를 가지며
이 포트는 지금 port의 data가 유효하고
읽을 수 있는 값임을 표현해 줍니다.
만약에 output port에 I/O protocol이 없다면
언제 데이터를 읽어야 할지를 확인하기 어렵습니다.
그래서 output port에는
항상 I/O protocol을 사용하는 것이 좋습니다.
Read와 Write둘다 하는 Function arguments는
input 과 output port가 분리됩니다.
위 코드예제에서 sum은
input은 sum_i로
output은 sum_o로
valid pin으로 sum_o_ap_vld를 가지는
I/O protocol과 함께
생성 됩니다.
만약에 function이 return valud를 가지고 있다면
return value 전달을 위해서
output port로 ap_return이 생성됩니다.
'design이 한번의 transaction을 끝냈을때' 가
C function수행이 한번 끝난 것과 동등하고
block-level protocols에서
함수가 끝난 것을 ap_done으로 표현합니다.
즉 ap_done pin은 ap_return의
valid pin 역할을 하게 됩니다.
참고. HLS에서 return value는
pointer를 사용 할 수 없습니다.
동작 예시로서 하단에 Default로 합성된
RTL Port의 Timing도를 확인해 봅니다.
1.
Design은 ap_start가 High일때 시작됩니다.
2.
ap_idle 신호는 동작과 동시에 Low로 내려갑니다.
3.
input data는 first cycle 이후에
어떤 사이클에서도 읽어 집니다.
Vivado HLS가 언제 읽기가 발생하는지를 조정합니다.
ap_ready signal은 입력을 읽는 것이 끝났을 때
high로 됩니다.
(다음 읽을 준비가 완료 되었다는 뜻이겠지요?
4.
Output sum이 계산되었을때,
output handshake(sum_o_ap_vld)는
데이터가 유효함을 나타냅니다.
5.
function의 동작이 끝났을때 ap_done이 동작하고
이것은 ap_return port의
output이 valid 함을 의미합니다.
6.
ap_idle는 다음 시작을 기다릴때
High 상태로 남습니다.
Interface Synthesis
I/O protocols의 결정
C argument,
default interface mode,
INTERFACE optimization directive
셋중 하나에 의해서 결정됩니다.
어떻게 결정되는지는 뒤에서
좀 더 살펴보도록 하겠습니다.
Interface Synthesis I/O protocols에서
어떤 type의 C argument를 사용하느냐에 따라서
프로토콜을 설정할 수 있거나 자동 설정 되는데
그것을 표현한 표가 있습니다!
해당 표는
아래의 약어를 보고 보시면 이해하기 좋습니다
D: 각 type에 따른 기본 interface mode
(Default interface mode for each type)
I : 읽기만 하는 input 요소
(Input arguments, which are only read)
O : 쓰기만 하는 출력 요소
(Output arguments, which are only written to)
I/O : 읽기 쓰기 다하는 요소
(Input/Output argument,
which are both read and written)
연한 회색깔은 Not Supported 입니다.
즉,
type에 따라 사용 불가능한 protocols이
있을 수 있다는 의미로 보입니다.
interface의 모든 detail한 부분들은
Interface Synthesis Reference 부분에
설명이 되어 있다고합니다.
같은 가이드의 466p쯤부터 시작되는데요
각 pin의 의미와 timing도를 보면서 설명해주기 때문에
좀 더 자세한 이해가 필요한 경우에
보기 좋은것 같습니다.
이제 부터는
Block-Level Interface Protocol,
Port-Level Interface Protocol의
선택지에 대해서 알아보게 되는데요
예를들어서 실제로 설정한다고 할때
이렇게 conv 함수의 Insert Directive를 선택하여
conv function의 Directive Editor에서
Interface Directive를 설정하는 경우의 mode의 종류는
Block-Level protocol interface로
위와 같이
ap_ctrl_chain
ap_ctrl_hs
ap_ctrl_none
s_axilite
가 선택가능한 것을 볼 수 있고
conv 함수의 port의 Directive Editor에서
Interface Directive를 설정하는 경우 mode의 종류
ap_ack
ap_bus
ap_fifo
ap_hs
ap_memory
ap_none
ap_ovld
ap_stable
ap_vld
axis
m_axi
s_axilite
등을 선택할 수 있는것을 볼 수 있습니다.
Block 별 Port별 interface protocols에 대해서 지금부터 알아보겠습니다.
Block-Level Interface Protocols
앞서서는 너무 간단하게 정리되었던
Block-Level Interface protocol에 대해서
좀 더 살펴보는 단계가 나와 있습니다.
Block-level interface는
ap_ctrl_none
ap_ctrl_hs
ap_ctrl_chain
s_axilite
등이 있다고 합니다.
이것들은 function또는 function의 return에 의해서
명확해진다고 하네요!
Vivado HLS의 GUI에서 directive를 명확히 할때,
이러한 protocol이 function의
return에 적용된다고 합니다.
함수가 return값이 없더라도
다른 protocol도 설정할 수 있다고 합니다.
ap_ctrl_hs mode의 경우
앞서 예제코드에서 보았던
default protocol과 같다고 합니다.
ap_ctrl_chain protocol은
ap_ctrl_hs와 유사한데
input port에 ap_continue가 있다고 합니다.
ap_continue는 block으로 부터 back pressure를 제공합니다.
함수가 완료 되었을때
ap_continue port가 0 이라면
block는 동작을 멈추고
다음 transaction이 진행되지 않을 것이고
다음 transaction은
ap_continue port가 1일 경우에만
동작이 된다 라는 겁니다.
ap_ctrl_none mode는 설계에
어떤 block-level I/O protocol도 없이 수행됩니다.
ap_ctrl_chain에 포함되는 ap_continue port에 의한 동작은
ug902 pdf의 469p에 나와있는데
궁금하신 분들은 해당부분을
자세히 읽어보시면 좋을것 같습니다!
해당 페이지에 나와있는 timing도를 첨부 합니다!
그림을 보시면
ap_ready지만 ap_continue에 의해서
return 값이 유지되고
ap_done도 유지되는
모습을 볼 수 있습니다.
앞서 나온 ap_xxxx와 약간 다른
s_axilite에 대한 이야기를 보겠습니다.
만약에 함수의 return 또한
AXI4-Lite interface(s_axilite)로 지정되면
block-level interface 내부의 모든 port들은
AXI4-Lite interface로 그룹지어집니다.
AXI4-lite interface는
CPU로 block의 start나 stop을 조작하는걸 구성할때
공통적으로 사용되는 practice 입니다.
여기까지 다뤄지고 이어서는
Port-Level Interface protocol에 대해
다룹니다.
Port-Level Interface
Port-Level Interface에는 여러가지 종류가 있지만
크게 4가지 분류로 나눠 볼 수 있습니다.
하나씩 살펴보겠습니다!
1. AXI4 interface
AXI4 interface는 Vivado HLS에서
AXI4-Stream(axis),
AXI4-Lite(s_axilite),
AXI4 master(m_axi),
등으로 지원합니다.
AXI4-Stream interface는
input argument이나
output argument만
지정할 수 있습니다.
input/output arguments는 사용이 불가 합니다.
AXI4-Lite interface는 stream을 제외한
어떤 type의 argument도
지정할 수 있습니다.
multiple argument들을
같은 AXI4-interface에 그룹 지을 수 있습니다.
AXI4 master interface는
array들이나 pointer들만 지정할 수 있습니다.
lite interface와 마찬가지로
multiple arguments를 같은
AXI4 interface에 group 지을 수 있습니다.
2. No I/O Protocol
ap_none 그리고 ap_stable mode를 선택하면
I/O protocol이 없는 port를 추가 할 수 있습니다.
이 mode는 argument가 data port로
부가적인 signal 없이 사용될때 선택합니다.
ap_none는 scalar input의 default mode 입니다.
ap_stable은 device가 reset mode일때
input 구성이 달라지는 경우에 사용합니다.
3. Wire Handshakes
Interface mode인 ap_hs는
two-way handshake signal을
data port와 함께 사용합니다.
Handshake는 산업계 표준인
valid and acknowledge handshake
입니다.
ap_vld mode는 같은 방식이지만
valid port만 가지고 있고
ap_ack는 같은 방식이지만
acknowledge port만 가지고 있습니다.
ap_ovld는 in-out argument들을 위해 사용됩니다.
ap_ovld를 사용하면
in-out은
input port와
output port로
분리 됩니다.
ap_none은 input port에 적용되고
ap_vld는 output port에 적용됩니다.
이것은 read와 write를 다하는
pointer argument의 default 값입니다.
ap_hs mode는 sequntial order에 따라
읽고 써지는 array에 적용 될 수 있습니다.
만약에 Vivado HLS가 read 또는 write access를
sequential하지 않게 하도록 할 수 있다면,
에러와 함께 합성이 중단 될겁니다.
만약 acccess 순서가 결정되어 질 수 없다면
Vivado HLS는 warning을 띄울 것입니다.
이게 무슨말인지 생각해봤습니다.
array에 접근하는 port를
handshake방식으로 하게 되면
valid pin과 ack pin만 추가 될것입니다.
따라서 데이터를 읽어오는건 당연히
sequential하게 접근하게 되는 것이고
당연히 array의 원소에 random하게
접근하는게 불가능할 것입니다.
따라서 array 원소에 random접근해야 한다면
그게 가능한 interface를 사용해야 할것입니다.
그래서 이어서 나오는
Port-Level Interface protocol이 바로
4. Memory Interface
Array argument들은
ap_memory interface가 default 입니다.
ap_memory interface는
standard block RAM interface로
data
address
chip-enable
write-enable
port로 구성되어 있습니다.
ap_memory interface는
single-port와
dual-port 방식으로
구성할 수 있습니다.
dual-port방식으로 interface를 결정하면
initial interval을 줄일수 있을 것입니다.
그래서 자동으로 dual-port로 수행될겁니다.
HLS에서 directive 설정할때
RESOURCE directive에서 array에 적용할
single-port block RAM을 interface로 선택하면
single-port block RAM interface가 적용됩니다.
거꾸로,
만약에 dual-port interface를
사용하는 것으로 VIAVDO HLS에서
RESOURCE directive에 명시 했는데
이 결정이 아무런 이점을 주지 못한다면
자동적으로
single-port interface로 수행이 된다고 합니다.
bram interface mode는 기능적으로
ap_memory interface와 동일하게 작동합니다.
유일한 차이점은 Vivado IP Integrator에서
design이 사용될때 뿐입니다.
ap_memory interface는
multiple and separate ports로 표시됩니다.
bram interface는 XIlinx block RAM과
single point-to-point connection 할 수 있는
단일 그룹 포트로 표시됩니다.
만약에 array가 sequential하게 접근 된다면
ap_fifo interface를 사용할 수 있습니다.
ap_hs interface와 마찬가지로
data access가 sequential하지 않다면
Vivado HLS는 중지되고 report에 경고가 나옵니다.
ap_fifo interface는
reading이나 writing 둘중 하나만 선택할 수 있습니다.
ap_bus interface는
bus bridge를 통해서 통신 할 수 있습니다.
이 interface는 특정 bus standard를 따르지는 않지만
시스템 버스와 차례대로 조정되는
버스 브릿지에 사용하기에 충분합니다.
The bus bridge must be able to cache all burst writes
우와... 내용이 너무 많네요...
오늘은 여기까지 하겠습니다!
'HW' 카테고리의 다른 글
[Verilog] Verilator tutorial (2) - waveform 만들기 (0) | 2020.07.23 |
---|---|
CHIPS Alliance(Common Hardware for Interface, Processors and Systems) // 하드웨어 관련 오픈소스 그룹 (0) | 2020.07.21 |
[Xilinx] hls::Mat 사용에 대해서 // HLS convolution tutorial 이해를 위해 (0) | 2020.04.21 |
Xilinx HLS tutorial (4) - Port 설정 (0) | 2020.04.16 |
Xilinx HLS tutorial (3) - Tcl Command Interface 사용하기 (0) | 2020.04.08 |