我在主机 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 内核来保持忙碌。上面的代码按预期工作。但是,第一次卸载 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),它可以工作。但是,我需要一个更永久的解决方案。任何人都可以对我的代码中出了什么问题有所了解。
谢谢