ArrayFire与原始CUDA编程



我对GPU编程很陌生,但由于我有一项计算密集型任务,我转向GPU以获得可能的性能提升。

我试着用ArrayFire Free版本重写我的程序。在启用多线程的情况下,它确实比我的CPU例程快,但没有达到我预期的程度(即<100%加速),并且返回的结果不太正确(假设CPU例程的结果正确,则与CPU例程相比错误<1%)。

我的任务主要是在大矩阵(300MB-500MB大小)上进行元素浮动-32数学运算,几乎没有如果/切换的情况等。我想性能瓶颈可能是CPU和GPU内存之间的带宽,因为有很多数据读取等。我测试的GPU是一个具有3GB视频内存的GeForce 580GTX。

如果我编写原始CUDA代码(使用CUBLAS等和平均优化)而不是使用ArrayFire执行任务,是否还有很大的优化空间?我阅读了一些NVIDIA优化指南;似乎有一些内存访问技巧可以更快地访问数据并减少银行冲突。ArrayFire是否自动使用这些通用技巧?

感谢您的帖子。很高兴听到初步结果加快了速度。我在ArrayFire工作,可以在这里回答您的问题。

首先也是最重要的一点,这里确实需要代码来帮助任何人实现特定性。你能分享你写的代码吗?

其次,你应该以以下方式思考CUDA和ArrayFire:CUDA是一种对GPU进行编程的方式,它为你提供了编写任何你想要的GPU代码的能力。但是,天真的CUDA代码(通常比CPU慢)和专业的、耗时的、手工优化的CUDA码之间有着巨大的区别。ArrayFire(以及CUBLAS等其他一些GPU库)已经进行了多年的优化,通常会给出比大多数普通人有时间自己实现的更好的结果。然而,人们使用ArrayFire(或其他库)的情况也存在差异。在使用ArrayFire库调用时,可以也应该调整一些变量,以获得最佳性能。如果你发布你的代码,我们可以在这里帮助分享其中的一些。

第三,ArrayFire在依赖BLAS的函数中使用了CULAS,因此直接使用CULAS不会有太大区别。

第四,是的,ArrayFire使用了NVIDIA CUDA编程指南中提供的所有优化(例如,加快数据传输和减少内存组冲突,就像你提到的那样)。这就是大部分ArrayFire开发的重点,优化这些事情。

最后,您注意到的数据差异可能是由于CPU与GPU计算的本质造成的。由于它们是不同的设备,您通常会看到略有不同的结果。这并不是说CPU比GPU能提供更好的结果,而是它们都以略微不同的方式以有限的精度工作。如果你使用的是单精度而不是双精度,你可能会考虑。发布代码也会让我们在这方面提供帮助。

很高兴在代码发布后扩展我的答案。

最新更新