Test contiguous pointers
Currently all array assignments using pointers will create a temporary array to ensure contiguous memory.
However, in nearly all cases are the used pointer arrays of contiguous layout and one may reduce the creation of temporary arrays by using this keyword.
I have tested adding contiguous at a relatively large set of arrays. But for a tiny system (4 atoms), it seems not important for such a small system.
I suspect it may have influence on a larger system.
Blueprint information
- Status:
- Complete
- Approver:
- None
- Priority:
- Undefined
- Drafter:
- Nick Papior
- Direction:
- Needs approval
- Assignee:
- Nick Papior
- Definition:
- Obsolete
- Series goal:
- None
- Implementation:
- Blocked
- Milestone target:
- None
- Started by
- Nick Papior
- Completed by
- Nick Papior
Related branches
Related bugs
Sprints
Whiteboard
Hi Nick,
The 'contiguous' keyword appears in F2008, and its implementation is still subject to interpretation.
Here is a test file to explore things.
! Simple tests for "array temporaries" and the influence of:
!
! - the use of the "contiguous" keyword
! - the use of pointers instead of allocatable arrays or simple arrays
!
! Results:
!
! gfortran 5.2 (checks at compile time with -Warray-
! (disable the call to is_contiguous, as it is not implemented...)
!
! The contiguous keyword has no effect.
! The use of pointers forces temporaries
! Non-contiguous sections are correctly flagged.
!
! intel 15.0.3 (checks at runtime). Use -check all -traceback
!
! The contiguous keyword is taken at face value, even if the
! case is obviously not contiguous, and no temporaries are produced.
! NOTE: According to Steve Lionel from Intel, this might have changed in recent
! versions
! (https:/
!
! On the other hand, the vanilla version of the routine correctly
! detects non-contiguous and contiguous cases (!!)
module m_interface
CONTAINS
SUBROUTINE MPI_BCAST( &
& BUFFER, COUNT, DATATYPE, ROOT, COMM, IERROR)
real, INTENT(INOUT) :: BUFFER(*)
INTEGER, INTENT(IN) :: COUNT
INTEGER, INTENT(IN) :: DATATYPE
INTEGER, INTENT(IN) :: ROOT
INTEGER, INTENT(IN) :: COMM
INTEGER, INTENT(OUT) :: IERROR
EXTERNAL MPI_BCAST_EXT
! CALL MPI_BCAST_EXT( &
! & BUFFER, COUNT, DATATYPE, ROOT, COMM, IERROR)
END SUBROUTINE MPI_BCAST
& BUFFER, COUNT, DATATYPE, ROOT, COMM, IERROR)
real, INTENT(INOUT), contiguous :: BUFFER(:)
INTEGER, INTENT(IN) :: COUNT
INTEGER, INTENT(IN) :: DATATYPE
INTEGER, INTENT(IN) :: ROOT
INTEGER, INTENT(IN) :: COMM
INTEGER, INTENT(OUT) :: IERROR
EXTERNAL MPI_BCAST_EXT
print *, is_contiguous(
! CALL MPI_BCAST_EXT( &
! & BUFFER, COUNT, DATATYPE, ROOT, COMM, IERROR)
END SUBROUTINE MPI_BCAST_CONT
end module m_interface
!
program tt
use m_interface
integer, parameter :: n = 20
real, dimension(n) :: a
real, pointer :: b(:)
real, dimension(n,n) :: c
real, allocatable :: d(:)
real, dimension(:,:), allocatable :: e
integer :: root, comm, ierror, count, datatype
allocate(b(n))
allocate(d(n))
allocate(
root = 0
datatype = 34
comm = 333
call mpi_bcast(
call mpi_bcast(
call mpi_bcast(
call mpi_bcast(
call mpi_bcast(
call mpi_bcast(
call mpi_bcast(
call mpi_bcast_
call mpi_bcast_
call mpi_bcast_
call mpi_bcast_
call mpi_bcast_
call mpi_bcast_
call mpi_bcast_
end program tt