对于神经网络加速器来说,需要考虑的主要指标有:
目标:最大化计算速度,最小化资源占用。
加速器验证思路:
Python/C++编写模块相同功能函数;testbench,记录模拟结果;addf16, mulf16mulmatsoftmax, laternorm

++++
对于重叠模式下的架构:这些PE算子可跨层复用,但使用了片外DDR,由PS与PL通信控制,计算延迟受限于通信带宽。

++++
其他加速器:
gp, hp, ready-validreg_ctrl, dma
半精度浮点数float16:常用于实现加速器中的浮点数运算。其结构:
|S| E | M |
16| |14 10|9 0|
FP16 = (-1)^S * 1.M * 2^(E - 15)
Range: [5.96*10^-8, 6.55*10^4]
++++
待定
对卷积层进行模块分解:
ConvLayer卷积层模块Tanh激活函数、 Softmax激活函数AvgPool平均池化层mulf16半精度浮点乘、addf16半精度浮点加一个卷积层有多个卷积核(Filter),image输入到不同的核得到不同的特征(Feature),自顶向下先观察Multi Filter Layer,其输入图像和六个卷积核,输出卷积结果。
网络ConvLayerMulti层输入矩阵规模:image 32*32, filterSet 5*5

++++
模块ConvLayerMulti层输入:
image: 1 * 32 * 32 * 16 = 16384
filters: 6 * 5 * 5 * 16 = 2400
outputConv: 1 * 28 * 28 * 16 = 12544
^ channel ^ scale ^ bitwidth

++++
对于单个卷积核(Filter),再观察Single Filter Layer,其输入图像和单个卷积核,输出特征图(Feature Map)。

++++
模块ConvLayerSingle层输入:
image: 1 * 32 * 32 * 16 = 16384
filters: 1 * 5 * 5 * 16 = 400
outputConv: 1 * 28 * 28 * 16 = 12544
^ channel ^ scale ^ bitwidth

一个卷积核(Filter)与一个输入图像(Image)进行卷积运算,得到特征图(Feature Map),这个过程通过ConvUnit模块实现。

++++
CU模块循环使用PE模块实现一个窗口的卷积操作,并输出一个半精度浮点型(FP16)计算结果。

卷积进行的具体操作是点乘,这里本质上是浮点算子:mulf16乘、addf16加,这里通过PE模块实现。

++++
元素处理(PE)模块:执行具体卷积操作,即权重与数据相乘后累加。添加result_reg,将电路从组合逻辑转化为时序逻辑,保证数据同步。

++++
元素处理(PE)模块代码演示:
module PE(
clk, rst,
fA, fB, res
);
parameter DATA_WIDTH = 16; // 数据位宽
input clk, rst;
input [DATA_WIDTH-1:0] fA, fB;
output reg [DATA_WIDTH-1:0] res;
wire [DATA_WIDTH-1:0] mul_res;
wire [DATA_WIDTH-1:0] add_res;
// 1. 计算乘法结果
mulf16 FMUL(.fA(fA), .fB(fB), .res(mul_res));
// 2. 计算累加结果
addf16 FADD(.fA(fA), .fB(fB), .res(add_res));
always @(posedge clk or posedge rst) begin
if(rst == 1'b1) begin
res <= 0;
end else begin
res <= add_res;
end
end
endmodule
Softmax函数将输入归一化,求得各个类概率。输入规模与输出规模相同(400)。

++++
计算过程(时序逻辑):
exponet求指数,FloatReciprocal计算指数模块exponent,求解$e^x$值,输入规模与输出规模相同(32),使用泰勒展开拟合:
- 两个乘法器:分子 & 分母。
- 一个加法器:累加。
对平均池化层分解:
AvgPoolMulti(通道平均池化)AvgPoolSingle(单通道平均池化)AvgU(平均池化单元)多通道平均池化层(Average Pool Multi)并行度为1,循环使用AvgPoolSingle完成所有通道的平均池化。(时序逻辑电路)

++++
单通道平均池化(Average Pool Single):全并行度,每个窗口都有一个AvgU运算模块。(组合逻辑电路)

平均池化单元(AvgU):每个通道的平均池化操作:求输入的四个数(位宽16 * 4)的均值,先求和,再乘以0.25得到均值(位宽16)。(组合逻辑电路)
优化:插入寄存器形成pipline。
对全连接层分解:
FCMulti(通道全连接)FCSingle(单通道全连接),激活函数为TanhPE计算模块全连接层(Full Connection Layer):进行线性计算,矩阵向量乘,向量和。
\[y = xW^T + b\]注意:多层之间加上
Tanh非线性激活函数。
PE是一个乘法器和加法器实现,实现累乘和累加。

参考如下CNN加速器目录:
.
├── vivado_project # 项目完整网络的vivado工程
├── conv_code # 不同并行度的卷积模块代码
├── final_code # 各模块以及网络顶层代码
│ ├── Part1. Convolution
│ ├── Part2. TanH Activation
│ ├── Part3. Softmax Activation
│ ├── Part4. Average Pooling
│ ├── Part5. Intergration
│ └── ...
├── test_scripts # 各个模块验证脚本
│ ├── Test1. ANN Test
│ ├── Test2. TanH Test
│ ├── Test3. Text Files Test
│ ├── Average Pooling Python Code
│ ├── Convolution Python Code
│ ├── Softmax Python Code
│ └── ...
├── results # 仿真截图,综合报告,验证数据表格
├── weights # 卷积与全连接层权重和偏置数据
├── hw_design.pdf # 项目硬件设计文档
└── README.md # 项目介绍