Xeon-Phi 从主机 openMP 并行区域异步卸载
Posted
技术标签:
【中文标题】Xeon-Phi 从主机 openMP 并行区域异步卸载【英文标题】:Xeon-Phi asynchronous offload from host openMP parallel region 【发布时间】:2014-04-24 16:38:44 【问题描述】:我在主机 openMP 代码中使用英特尔的卸载编译指示。代码如下所示
int s1 = f(a,b,c);
#prama offload singnal(s1) in (...) out(x:len)
for (int i = 0; i < len; ++i)
x[i] = ...
#pragma omp parallel default(shared)
#pragma omp for schedule(dynamic) nowait
for (int i = 0; i < count; ++i)
/* code */
#pragma omp for schedule(dynamic)
for (int j = 0; j < count2; ++j)
/* code */
#pragma offload wait(s1)
/* code */
$x$ 的代码卸载计算到 MIC。代码通过将一些 openMP 分配给 CPU 内核来保持忙碌。上面的代码按预期工作。但是,第一个 offload pragma 需要花费很多时间,并且已经成为瓶颈。尽管如此,总体而言,将 $x$ 的计算卸载到 MIC 是值得的。我正在尝试解决此延迟问题的一种方法如下
int s1 = f(a,b,c);
#pragma omp parallel default(shared)
#pragma omp single nowait
#prama offload singnal(s1) in (...) out(x:len)
for (int i = 0; i < len; ++i)
x[i] = ...
#pragma omp for schedule(dynamic) nowait
for (int i = 0; i < count; ++i)
/* code */
#pragma omp for schedule(dynamic)
for (int j = 0; j < count2; ++j)
/* code */
#pragma offload wait(s1)
/* code */
所以这个新代码分配了一个线程来执行卸载,而其他 openmp 线程可以用于其他工作共享结构。但是,此代码不起作用。我收到以下错误消息
device 1 does not have a pending signal for wait(0x1)
卸载报告指出上述代码是罪魁祸首。一种临时解决方法是使用常量作为信号,即信号(0),它可以工作。但是,我需要一个更永久的解决方案。任何人都可以对我的代码中出了什么问题有所了解。
谢谢
【问题讨论】:
这是software.intel.com/en-us/forums/topic/509845的副本 【参考方案1】:让我补充一下 Taylor 的回复。
第一次卸载确实比后续卸载花费更多时间,因为正在进行初始化工作。泰勒勾勒了那里发生的一些事情。您可以通过使用环境变量 OFFLOAD_INIT=on_start 来避免虚拟卸载。这应该让运行时系统提前完成所有初始化。这样做的开销并没有消失,但它会从您的第一次卸载转移到应用程序初始化。
您的第二个代码 sn-p 的问题似乎是您的卸载针对不同的设备。仅当信号和等待发生在同一目标设备上时,信号和等待才有效。由于您没有在卸载时明确使用 target(mic:0)
子句,因此运行时系统选择不同目标设备的可能性很高。
我想提出的一个建议是不要使用纯整数作为信号。通常,该信号表明某个缓冲区已准备就绪。在这些情况下,最好使用缓冲区指针作为信号句柄,因为它对于使用不同缓冲区的并发卸载来说是唯一的。
干杯, -迈克尔
【讨论】:
他们针对的是同一个设备。即麦克风:1。这是明确完成的【参考方案2】:我无法评论第二个代码块。我对第一个有一些看法。
第一次卸载总是需要更长的时间,因为它还设置了卸载基础架构。该结构包括诸如传递环境变量、复制 libomp5 的 mic 实现、设置线程池等内容。
避免这种情况的方法是首先设置一个虚拟卸载,这意味着它实际上并没有做任何事情并且不是您的计算块的一部分。
software.intel.com/mic-developer 的培训选项卡下提供了一组关于优化至强 phi 协处理器的优秀参考资料。
还可以查看 software.intel.com/en-us/articles/programming-and-compiling-for-intel-many-integrated-core-architecture、software.intel.com/en-us/articles/ optimization-and-performance-tuning-for-intel-xeon-phi-coprocessors-part-1-optimization 和 software.intel.com/en-us/articles/optimization-and-performance-tuning-for-intel-xeon -phi-coprocessors-part-1-优化。
抱歉,URL 太长了,但由于我是新手,*** 不允许包含两个以上的链接。
【讨论】:
感谢您的回复。整个代码块都在一个连续的 for 循环中。因此,在外部 for 循环的每次迭代中都会调用函数。初始化在外部 for 循环之前完成。在我的情况下,这个初始化需要 7 秒(由于大量的 malloc)。在一轮 malloc 之后,每个分配的区域都被“重用”。我完全忽略了这 7 秒。它是内部外部循环,每个 MIC 卸载需要 4 毫秒,这是我想要隐藏的。以上是关于Xeon-Phi 从主机 openMP 并行区域异步卸载的主要内容,如果未能解决你的问题,请参考以下文章
我应该在 openMP 并行区域内使用 gnu 并行模式函数吗(for-loop,tasks)