OpenCL是一种面向多设备、多平台的编程语言,被多个设备生产厂家支持,具有良好的兼容性。但是,由于不同设备之间有很大的差异,在不同设备上针对OpenCL的调优手段也大不相同。这里主要针对两款GPU,分别是ARM公司的Mali-T860(以下简称为T860)和NVIDIA公司的GeForce GTX 950M(以下简称为950M),使用不同的内存优化策略,评估1024*1024规模的矩阵相乘的性能(c = a * b)。重点分析了两类的内存优化策略:
- 矩阵所使用的内存的分配位置。主要包括是在host上分配还是在device上面分配,以及调用clCreateBuffer函数时,采用不同的参数所对应的结果。
- Kernel函数的优化手段,主要分析OpenCL的local内存的使用对性能的影响。
矩阵内存分配位置对性能的影响
调用clCreateBuffer函数时,有3个flag参数会影响到矩阵的分配位置。
- CL_MEM_COPY_HOST_PTR。原始的数据在host端。在device端创建cl_mem对象,分配内存,并把数据从host端复制到device端。
- CL_MEM_USE_HOST_PTR。原始的数据在host端。在device端创建cl_mem对象,使用host端的数据,也有可能会产生从host端复制数据到device端的行为。
- CL_MEM_ALLOC_HOST_PTR。原始的数据在device端分配。在device端创建cl_mem对象,并且在host可访问的区域为该对象分配内存。也就是说,可以把这样的对象map(调用clEnqueueMapBuffer)到host端,然后从host端访问。
表1和表2给出了两款GPU下,3种不同的内存分配方式下,矩阵运算对应的性能。矩阵运算采用了相同的kernel。
表1 T860下不同内存分配方式的性能(单位: ms)
当参数为CL_MEM_USE_HOST_PTR时,矩阵a,b都在host端使用m