Page 327 - 《软件学报》2020年第9期
P. 327
2948 Journal of Software 软件学报 Vol.31, No.9, September 2020
DRAM,其存储容量最大,一般在数十 GB,用于存放 GPU 程序的输入和输出数据;但其访存延迟比较高.对全局
内存的访问一般会经过高速缓存.二级高速缓存(L2 cache)由所有流多处理器共享,容量一般为数 MB.一级高速
缓存(L1 cache)位于流多处理器内部,由位于同一个流多处理器上的线程共享,容量一般为数十 KB.最快的存储
部件是寄存器.一个流多处理器一般集成了数万个 32 位寄存器.这些寄存器被划分给不同的线程使用.另外,流
多处理器上还有两种比较特殊的存储部件:共享内存(shared memory)是一块由编程人员手工控制使用的存储
空间,容量一般为数十 KB,可以用于缓存程序执行中频繁访问的数据;而常量缓存(constant cache)可以用来缓存
对常量内存的访问.常量内存也位于 DRAM 中,由编译器和驱动程序使用,一般用于保存在整个 GPU 程序生命
周期中取值不变的数据.当常量缓存命中时,访问延迟很低.对常量内存的访问往往不经过高速缓存.常量缓存
访问的另一个特点是:当一个 warp 内的线程访问常量内存中的相同位置时,这些线程的访问请求会被合并,并
通过一次请求获得结果.
Fig.3 GPU memory hierarchy
图 3 GPU 存储层次示意图
2 稀疏感知的算子代码生成
本节介绍所提出的稀疏感知的算子代码生成方法.我们首先介绍我们设计的算子模板,在模板设计中,我们
考虑了多种针对 GPU 平台的优化;接下来,我们介绍我们基于算子模板设计的中间表示模板以及基于中间表示
模板的分析和稀疏算子代码的生成过程;最后,我们分析了生成稀疏算子代码中的访存优化.我们主要以卷积算
子为例,具体说明我们的稀疏算子代码生成过程.
2.1 算子模板
在 GPU 平台上有多种卷积的计算方法,包括基于矩阵乘法(GEMM)的方法和直接卷积等.基于 GEMM 的方
法需要对输入数据进行变换,这一过程需要对输入数据进行复制,增大了访存需求.考虑到通用性和稀疏计算的
计算密度问题,我们基于直接卷积的方式设计我们的卷积算子模板.我们首先定义要用到的符号.我们分别使用
Input,Weight 和 Output 表示输入数据、卷积参数和卷积输出,其中 Input∈R N*C*H*W ,Weight∈R K*C*R*S ,Output∈
R N*K*H′*W′ .各个维度的含义见表 1.维度的大小用大写字母表示,而每个维度上的循环变量用相应的小写字母表
示.同时,我们使用下标表示某个具体位置的元素,如 Input n,c,h,w .
Table 1 Definition of symbols in convolution
表 1 卷积中使用的符号定义
名称 描述
N 输入数据批大小
C 输入数据通道数目
H/W 输入数据高/宽
K 卷积核数目
R/S 卷积核的高/宽
H′/W′ 卷积计算结果的高/宽