我尝试用OpenMP并行化C++中程序的一个热点,但是它不能扩展。 1个线程需要25秒,而2个线程只需要21秒。我使用Intel VTune Amplifier进行了Locks&Wait分析,但这并没有真正帮助我。看起来像:

我尤其不明白mkl_blas_dcopy来自何处以及它叫什么(即使我删除了并行区域,我也有这个调用和时间轴中的第二个线程)。

我试图从“自顶向下的树”中获取更多信息,但这对我没有太大帮助。

高级热点分析也没有给我更多信息。
为了识别问题,我该如何处理该问题?

附加信息:在我的整体运行时更糟之前,但是我在串行代码中做了很多优化,可以提高性能,但是之后我的代码不再扩展。

提前谢谢了!

编辑:这里也是时间线,其中没有显示过渡,与我放大的距离无关。在这种情况下,我使用了另一个具有8个线程的测试用例。

最佳答案

  • 您使用什么版本的VTune?看起来不是最新的-屏幕快照上的OpenMP区域的帧速率已在当前版本中删除。值得尝试的是2015年新的更新1,对OpenMP分析进行了一些修复和改进。
  • 您使用什么编译器和OpenMP运行时?如果它是Intel OpenMP(和编译器),则VTune分析将为OpenMP地区提供更多信息。只需将“自下而上”中的分组从“Funcion/callstack”更改为“OpenMP region/...”,您会发现很多有趣的事情。
  • 您会看到mkl_blas_dcopy,因为您似乎在代码中使用了MKL函数。 mkl_blas_dcopy只是一个内部MKL函数。在自下而上选择“mkl_blas_dcopy”热点时,您可以在右侧的堆栈面板中的代码中找到实际的MKL调用-您应该可以看到到main()的调用链。
  • MKL已与OpenMP并行化。您可能会将MKL调用放在自己的OpenMP区域内。如果是这种情况,那不是最佳选择-嵌套时OpenMP不好。您应该选择在不具有OpenMP的情况下使用MKL的并行版本,或者在OpenMP并行区域内使用串行MKL库。您可以通过链接控制串行/并行MKL设置,请参见MKL Link Advisor:https://software.intel.com/en-us/articles/intel-mkl-link-line-advisor
  • 屏幕快照中时间轴上的每个帧都可能是MKL的OpenMP区域。似乎存在许多持续时间较短的并行区域,这可能表明从循环中调用了MKL。因此,每次迭代都会启动,执行和停止OpenMP并行区域。启动和停止操作会有一些开销,这要花大量的等待时间。因此,可能值得在外部OpenMP循环中尝试串行MKL版本,以避免多个并行区域重新进入。
  • 关于c++ - 如何解释英特尔VTune放大器的“锁与等待”,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/27034950/

    10-13 03:32