Closing Channels in Co-array Fortran
program closing_channels
use iso_fortran_env, only: int32, real64
implicit none
integer(int32) :: j
logical :: more, ok
! In this example we'll use a `jobs` array to communicate work to be done
! from the main program to a worker image. When we have no more jobs for
! the worker we'll use synchronization to indicate completion.
integer(int32), codimension[:] :: jobs(5)[*]
logical, codimension[:] :: done[*]
! Here's the worker image. It repeatedly receives from `jobs` until
! synchronization indicates that all jobs have been processed.
! We use this to notify on `done` when we've worked all our jobs.
if (this_image() == 2) then
do
sync images(1)
if (jobs(1)[1] == -1) then
print *, "received all jobs"
done[1] = .true.
exit
else
print *, "received job", jobs(1)[1]
jobs(1)[1] = 0 ! Mark job as processed
end if
end do
end if
! This sends 3 jobs to the worker over the `jobs` array,
! then signals completion.
if (this_image() == 1) then
do j = 1, 3
jobs(1)[2] = j
print *, "sent job", j
sync images(2)
end do
jobs(1)[2] = -1 ! Signal end of jobs
print *, "sent all jobs"
sync images(2)
! We await the worker using synchronization.
do while (.not. done[2])
sync images(2)
end do
! In Co-array Fortran, we don't have the concept of closed channels.
! Instead, we use explicit synchronization and flags to indicate
! completion of work.
print *, "All jobs processed"
end if
end program closing_channels
To run this Co-array Fortran program:
$ caf closing_channels.f90 -o closing_channels
$ cafrun -np 2 ./closing_channels
sent job 1
received job 1
sent job 2
received job 2
sent job 3
received job 3
sent all jobs
received all jobs
All jobs processed
In this Co-array Fortran version, we use coarrays and image synchronization to mimic the behavior of channels in Go. The jobs
array is used to communicate jobs between images, and the done
logical coarray is used for synchronization.
Instead of goroutines, Co-array Fortran uses multiple images (similar to MPI processes) for parallel execution. The program is designed to run with two images: image 1 sends jobs and image 2 receives and processes them.
The concept of closing a channel is replaced with sending a special value (-1 in this case) to indicate that no more jobs will be sent. The worker image (image 2) checks for this value to know when to stop processing jobs.
Note that the exact output order may vary due to the parallel nature of the program, but the overall behavior should be similar to the original Go program.