A call to move_alloc with coarray arguments fall under image control statements (statements that affects the execution ordering between images).
From J3/24-007, 16.9.147, paragraph 5:
When a reference to MOVE_ALLOC is executed for which the FROM argument is a coarray, there is an implicit synchronization of all active images of the current team. On those images, execution of the segment (11.7.2) following the CALL statement is delayed until all other active images of the current team have executed the same statement the same number of times. When such a reference is executed, if any image of the current team has stopped or failed, an error condition occurs.
Imagine a 2-d stencil iteration in pseudo-code (may have errors
):
real(dp), allocatable, codimension[*] :: f1(:,:), f2(:,:)
real(dp) :: residual, tol
! ... initialize ...
iterate: do
call sweep(from=f1, to=f2)
call fill_and_exchange_boundaries(f2)
sync all
residual = maxval(abs(f2 - f1))
call co_max(residual)
if (residual < tol) exit iterate
swap: block
real(dp), allocatable tmp(:,:)[*]
call move_alloc(f2,tmp) ! sync
call move_alloc(f1,f2) ! sync
call move_alloc(tmp,f1) ! sync
end block swap
end do iterate
To avoid the synchronization which results from the symmetric memory of a coarray allocatable object, I suppose one has to do something like this instead (keep allocatable and codimension attributes separated):
type :: grid_t
real, allocatable :: f1(:,:), f2(:,:)
end type
type(grid_t) :: grid[*]
iterate: do
call sweep(grid%f1,grid%f2)
call fill_boundaries(grid%f2)
call exchange(grid) ! exchange halo regions across images
sync all
if (...) exit iterate
call swap(grid%f1, grid%f2) ! uses `move_alloc` on local objects
end do iterate