java - 如何测量 OpenCL 读出时间?

标签 java performance profiling opencl

我想确保 clEnqueueReadBuffer() 的测量时间如何测量将数据从 GPU 复制到主内存所需的时间的正确方法。我有点怀疑clFinish()也确实做出了贡献。

我运行 1000000 个 float 的 100 倍点积,并以此测量时间

  // RUN TIME BLOCK
  println( " Running OpenCL program ... " );
  t1 = System.nanoTime(); 
  for (int reps = 0; reps < 100; reps++) {
    clEnqueueNDRangeKernel(commandQueue, kernel, 1, null, global_work_size, local_work_size, 0, null, null);    
  }
  clFinish(commandQueue); // VERSION 1
  t2 = System.nanoTime(); 
  println( " OpenCL Run Time : "+ ((t2-t1)*1e-9)+" [s] " );

  // READ OUT TIME BLOCK
  t1 = System.nanoTime(); 
  //clFinish(commandQueue); // VERSION 2
  clEnqueueReadBuffer(commandQueue, memObjects[2], CL_TRUE, 0, n * Sizeof.cl_float, dst, 0, null, null);
  t2 = System.nanoTime(); 
  println( " Read-out Time: "+ ((t2-t1)*1e-9)+" [s] " );

得到结果

 OpenCL Run Time : 2.5124469 [s] 
 Read-out Time: 0.002145424 [s] 

这对我来说似乎有点太好了,只有 2 毫秒和 < 总时间的 0.1% ... CPU-GPU 通信瓶颈的问题似乎并没有那么严重。

当我输入clFinish(commandQueue);时里面Read-out Time阻止我得到这些结果

OpenCL Run Time : 1.0892084 [s] 
Read-out Time: 1.4300439 [s] 

另一方面,这似乎太糟糕了……在 GPU 上执行 100 次乘法比通过 PCI-express 复制要快? ....也许吧

<小时/>

只是为了完整性:

我用了openclp5 processing 的库其中使用 jocl在 Ubuntu 12.04 64 位上使用 Java jdk 1.7,配备 Quadro FX 580 GPU 和

我的内核很简单(没有优化或任何东西)

  String programSource =     
   "__kernel void sampleKernel(                                                 "+
   "__global const float *a, __global const float *b, __global float *c) {      "+
   "  int gid = get_global_id(0);                                               "+
   "  c[gid] = a[gid] * b[gid];                                                 "+
   "}";

最佳答案

您测量将数据读回主机的时间的第一种方法是正确的。第二种方法需要一些计算时间。

您正在读取的数据量为1000000 * sizeof(float) = 4MB。如果这需要 2 毫秒,则意味着您将获得 4MB/0.002s = 2 GB/s 的带宽。为什么你认为这好得令人难以置信?您的卡支持 PCIe x16,理论峰值带宽为 8 GB/s(单向)。

关于java - 如何测量 OpenCL 读出时间?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/24120298/

相关文章:

java - 根据用户输入查找数组中的最大数字

java - 什么是 “reached end of file while parsing”错误,以后如何避免该错误?

c# - 快速搜索集合中的对象

javascript - 我的 C++ 代码比 JavaScript 代码慢很多

java - 用于分析大型 Java 堆转储的工具

java - 如何从 Edittext Preference 捕获用户输入?

python - 简单千层面网络输出很慢

go - 为什么在 Go 中锁定比 Java 慢得多?很多时间花在 Mutex.Lock() Mutex.Unlock()

c# - 是否有针对 .Net 解决方案(如 VisualVM for Java)的监控和分析工具?

java - GCM 和 Smack API