Intel® Fortran Compiler 16.0 User and Reference Guide
A DO construct can contain one or more complete DO constructs (loops). The range of an inner nested DO construct must lie completely within the range of the next outer DO construct. Nested nonblock DO constructs can share a labeled terminal statement.
The following figure shows correctly and incorrectly nested DO constructs:
In a nested DO construct, you can transfer control from an inner construct to an outer construct. However, you cannot transfer control from an outer construct to an inner construct.
If two or more nested DO constructs share the same terminal statement, you can transfer control to that statement only from within the range of the innermost construct. Any other transfer to that statement constitutes a transfer from an outer construct to an inner construct, because the shared statement is part of the range of the innermost construct.
When the nested DO constructs contain no statements between the DO statements in the nest of DO constructs, the nest is called “perfectly nested”. When perfectly nested DO constructs are modified by a COLLAPSE clause in any of these OpenMP* directives:
There are restrictions on which general compiler directives (see General Compiler Directives) and OpenMP Fortran compiler directives (see OpenMP Fortran Compiler Directives) can appear before the DO statements in the nested DO construct:
In the following example, COLLAPSE (1) on affects the DO I loop. Therefore general directives before the DO J loop, which is at level 2, are allowed:
!$OMP SIMD collapse (1) !dir$ prefetch … ! this is allowed since it is before the start ! of the perfectly nested DO construct do i = … !dir$ loop count … ! this is allowed since collapse only applies ! to the i-loop, not the j-loop do j = … enddo ! end for j-loop enddo ! end for i-loop
In the following example, COLLAPSE (2) affects the DO I loop and the DO J loop but not the DO k loop.
!$OMP SIMD collapse (2) !dir$ prefetch … ! this is allowed since it is before the start ! of the perfectly nested DO construct do i = … do j = … !dir$ loop count … ! this is allowed since collapse only applies to ! the i-loop and the j-loop, not the k-loop do k= …. enddo ! end for k-loop enddo ! end for j-loop enddo ! end for i-loop
In the following example, COLLAPSE (2) affects the DO I loop and the DO J loop so there can be no directives before the DO J loop.
!$OMP SIMD collapse (2) !dir$ prefetch … ! this is allowed since it is before the start ! of the perfectly nested DO construct do i = … !dir$ loop count … ! this is not allowed: it is breaks the perfectness ! of the i-loop and the nj-loop collapsing do j = … enddo ! end for j-loop enddo ! end for i-loop