跳过导航链接 | |
退出打印视图 | |
Oracle Solaris Studio 12.3:OpenMP API 用户指南 Oracle Solaris Studio 12.3 Information Library (简体中文) |
要启用作用域检查,请使用 -xvpara 和 -xopenmp 选项在优化级别 -xO3 或更高级别上编译 OpenMP 程序。如果只使用 -xopenmp=noopt 来编译程序,作用域检查将不起作用。如果优化级别低于 -xO3,编译器将发出警告消息,且不执行任何作用域检查。
在作用域检查期间,编译器将检查所有 OpenMP 构造。如果确定有些变量的作用域时引发问题,编译器会发出警告消息,有时还会建议使用正确的数据共享属性子句。
例如:
示例 7-1 作用域检查
% cat t.c #include <omp.h> #include <string.h> int main() { int g[100], b, i; memset(g, 0, sizeof(int)*100); #pragma omp parallel for shared(b) for (i = 0; i < 100; i++) { b += g[i]; } return 0; } % cc -xopenmp -xO3 -xvpara source1.c "source1.c", line 10: Warning: inappropriate scoping variable 'b' may be scoped inappropriately as 'shared' . write at line 13 and write at line 13 may cause data race "source1.c", line 10: Warning: inappropriate scoping variable 'b' may be scoped inappropriately as 'shared' . write at line 13 and read at line 13 may cause data race
如果优化级别低于 -xO3,编译器将不进行作用域检查:
% cc -xopenmp=noopt -xvpara source1.c "source1.c", line 10: Warning: Scope checking under vpara compiler option is supported with optimization level -xO3 or higher. Compile with a higher optimization level to enable this feature
以下示例显示了潜在的作用域错误:
示例 7-2 作用域错误示例
% cat source2.c #include <omp.h> int main() { int g[100]; int r=0, a=1, b, i; #pragma omp parallel for private(a) lastprivate(i) reduction(+:r) for (i = 0; i < 100; i++) { g[i] = a; b = b + g[i]; r = r * g[i]; } a = b; return 0; } % cc -xopenmp -xO3 -xvpara source2.c "source2.c", line 8: Warning: inappropriate scoping variable 'r' may be scoped inappropriately as 'reduction' . reference at line 13 may not be a reduction of the specified type "source2.c", line 8: Warning: inappropriate scoping variable 'a' may be scoped inappropriately as 'private' . read at line 11 may be undefined . consider 'firstprivate' "source2.c", line 8: Warning: inappropriate scoping variable 'i' may be scoped inappropriately as 'lastprivate' . value defined inside the parallel construct is not used outside . consider 'private' "source2.c", line 8: Warning: inappropriate scoping variable 'b' may be scoped inappropriately as 'shared' . write at line 12 and write at line 12 may cause data race "source2.c", line 8: Warning: inappropriate scoping variable 'b' may be scoped inappropriately as 'shared' . write at line 12 and read at line 12 may cause data race
此虚构示例显示了作用域检查可以检测到的一些典型作用域错误。
r 被指定为归约变量,其操作为 +,但实际上操作应为 *。
a 的作用域显式确定为 PRIVATE。由于 PRIVATE 变量没有初始值,因此第 11 行中对 a 的引用可能会显示乱码。编译器会指出此问题,并建议程序员考虑将 a 的作用域确定为 FIRSTPRIVATE。
变量 i 是循环索引变量。有些情况下,如果在循环后使用循环索引值,程序员可能希望将其指定为 LASTPRIVATE。但在示例中,在循环后根本没有引用 i。编译器会发出警告,并建议程序员将 i 的作用域确定为 PRIVATE。使用 PRIVATE 而不是 LASTPRIVATE 可以提高性能。
程序员不为变量 b 显式指定数据共享属性。根据 OpenMP 3.0 规范第 79 页的第 27-28 行,将 b 的作用域隐式确定为 SHARED。但是,将 b 的作用域确定为 SHARED 将导致数据争用。b 的正确数据共享属性应为 REDUCTION。