[英]OpenMP nesting not turning off
我正在嘗試使用 OpenMP(4.5,通過 GCC 7.2.0)管理嵌套的並行區域,但在關閉嵌套時遇到了一些問題。
示例程序:
#include <stdio.h>
#include <omp.h>
void foobar() {
int tid = omp_get_thread_num();
#pragma omp parallel for
for (int i = 0; i < 4; i++) {
int otid = omp_get_thread_num();
printf("%d | %d\n", tid, otid);
}
}
int main(void) {
omp_set_nested(0);
#pragma omp parallel
{
foobar();
}
printf("\n");
foobar();
return 0;
}
我期望在這里發生的是 foobar() 上的並行區域和非並行調用都將吐出 4 行,這與
// parallel region foobar()
0 | 0
1 | 1
2 | 2
3 | 3
// serial region foobar()
0 | 0
0 | 1
0 | 2
0 | 3
因為我不允許嵌套並行。 但是,我在具有正確 TID 的並行區域內得到 16 行,但 OTID 始終為 0(即每個線程都產生 4 個自己的線程,並在其上執行整個循環)並且我在外部得到 4 行(即並行因為正如我所期望的那樣產生 4 個線程)
我覺得我在這里遺漏了一些非常明顯的東西,有人能幫我解釋一下嗎? 是否禁用嵌套應該將該 omp 並行轉換為常規 omp for,並相應地分配工作?
您的問題來自錯誤的假設,即omp for
指令將被解釋並且相應的工作分布在線程之間,而不管哪個parallel
區域處於活動狀態。 不幸的是,在您的代碼中, omp for
僅與函數foobar()
聲明的parallel
區域相關聯。 因此,當這個區域被激活時(意思是因為你禁用了嵌套的並行性,當foobar()
不被另一個parallel
區域調用時)你的循環將分布在新生成的線程中。 但如果不是,因為foobar()
是從另一個parallel
區域調用的,那么omp for
被忽略並且循環不會在調用線程之間分布。 因此,它們中的每一個都執行整個循環,從而導致您看到的printf()
的復制。
一個可能的解決方案是這樣的:
#include <stdio.h>
#include <omp.h>
void bar(int tid) {
#pragma omp for
for (int i = 0; i < 4; i++) {
int otid = omp_get_thread_num();
printf("%d | %d\n", tid, otid);
}
}
void foobar() {
int tid = omp_get_thread_num();
int in_parallel = omp_in_parallel();
if (!in_parallel) {
#pragma omp parallel
bar(tid);
}
else {
bar(tid);
}
}
int main() {
#pragma omp parallel
foobar();
printf("\n");
foobar();
return 0;
}
我真的不覺得這個解決方案完全令人滿意,但我現在看不到任何更好的解決方案。 也許以后我會得到一些啟示......
編輯:好吧,我有另一個想法:反過來做並強制嵌套並行性,每當從實際parallel
區域調用函數時,只有一個活動線程:
#include <stdio.h>
#include <omp.h>
void foobar() {
int tid = omp_get_thread_num();
omp_set_nested(1);
#pragma omp single
#pragma omp parallel for
for (int i = 0; i < 4; i++) {
int otid = omp_get_thread_num();
printf("%d | %d\n", tid, otid);
}
}
int main() {
#pragma omp parallel
foobar();
printf("\n");
foobar();
return 0;
}
這一次代碼看起來更好,沒有任何重復,並給出(例如):
$ OMP_NUM_THREADS=4 ./nested
3 | 2
3 | 3
3 | 1
3 | 0
0 | 3
0 | 1
0 | 0
0 | 2
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.