j3-fortran / fortran_proposals

Proposals for the Fortran Standard Committee
178 stars 15 forks source link

Allow higher integer kinds for event count inside event_type #111

Open milancurcic opened 4 years ago

milancurcic commented 4 years ago

Problem

Currently the standard defines the event_type to have an internal event count that is an integer with atomic_int_kind. When you make event post(), the event count is incremented by 1. If you do event wait() on the event, the count is decremented by 1, or until_count if provided. However event wait() is a blocking statement. To do non-blocking polling of events, Fortran 2018 provides the intrinsic subroutine event_query().

As far as I can tell, the standard doesn't dictate the size of atomic_int_kind. On my platform (gcc-9.2.0, OpenCoarrays-2.8.0), atomic_int_kind is the same as int32, which has the maximum value of 2147483647. You can see where this is going: If you post events from one or more images, and poll them using event_query(), the event count may go out of range in long-running programs.

What happens if the event count range is exceeded? I don't think the standard specifies.

Example

Compile, then run this program on two or more images:

program event_count_limit

  use iso_fortran_env, only: event_type, int64
  implicit none
  type(event_type) :: event[*]
  integer(int64) :: n = 0

  if (this_image() == 1) then
    do
      call event_query(event, n)
      print *, n, '/', huge(n)
      call execute_command_line('sleep 1')
    end do
  else
    do
      event post(event[1])
    end do
  end if

end program event_count_limit

(I use int64 for n intentionally to demonstrate that the limit is in the internal count representation)

You should get the output like this:

                   13 /  9223372036854775807
              5878597 /  9223372036854775807
             11904877 /  9223372036854775807
...
           2120568619 /  9223372036854775807
           2126577421 /  9223372036854775807
           2132538217 /  9223372036854775807
           2138522898 /  9223372036854775807
           2144551285 /  9223372036854775807
          -2144391377 /  9223372036854775807
          -2138394635 /  9223372036854775807
          -2132374894 /  9223372036854775807
...

If I post continuously from 5 images, my event count overflows in ~10 minutes. If the event count were a higher integer kind, e.g. int64, it would overflow in > ~70000 years.

Solution

Introduce higher atomic kinds to iso_fortran_env, e.g. atomic_int64_kind, and:

use iso_fortran_env, only: atomic_int64_kind, event_type
type(event_type) :: notification[*]
notification = event_type(count_kind=atomic_int64_kind)

Note

This issue was raised by my technical editor while reviewing my chapter draft on teams, events, and collectives, paraphrasing: "What happens if the maximum event count is exceeded in long-running programs?". I didn't think of this until he asked.