next up previous contents index
Next: L. HPF Intrinsic and Up: ADAPTOR HPF Language Reference Previous: J. Task Parallelism   Contents   Index

Subsections


K. Extrinsic Procedures

ADAPTOR supports the EXTRINSIC facilities of HPF for serial and local routines. Local and serial routines can be written in FORTRAN 77 or in HPF itself.

local routines:
a local routine allows to write single-processor code that works only on data that is mapped to a given physical processor. In this sense, a local routine contains only local computations and will be executed independently by all processors on which the routine is invoked.

Nevertheless it might be possible to call message passing commands within a local routine, but in this case the user itself is responsible for any communication. But only local data can be accessed within the local routine. Local routines can also be used to provide an HPF interface to implementation-specific parallel libraries.

serial routines:
a serial routine allows to write code that will only be executed by a single physical processor.


K..1 HPF_LOCAL Procedures

HPF_LOCAL routines allow to write code that only works on local part of the arrays. ADAPTOR does not act on mapping directives of the arrays within the routine, so the code will work for all kind of actual arguments.

      extrinsic (HPF_LOCAL) subroutine S (A, COL)
      real, dimension :: A(:,:)
      integer :: COL
      ....                   ! code that works on the local part of A
      end subroutine S

From the caller's standpoint, an invocation of a local procedure from a ''global`` HPF program has the same semantics as an invocation of a regular procedure.

If one processor is executing a local routine, it might be possible that only some processors are executing this incarnation. Therefore in a local routine it is not possible to have any global operation like redistribution or calling global routines. So we have the following restrictions for local routines:

As already mentioned, the user can call any message passing code within local routines. But then he is itself responsible that the routine is executed by all participating processors.

K..1.1 HPF Local Routine Library

Local HPF procedures can use any HPF intrinsic or library procedures. In addition, a set of local library routines are provided that can be used to get more information about the global view of the actual arguments.

      use HPF_LOCAL_LIBRARY

The routines of the HPF Local Library are listed in the Appendix E.

K..1.2 Message Passing in HPF_LOCAL Routines

Processors executing a local HPF routine can communicate with each other. The context is given by the last global HPF context in which the local routine has been called.

The routines are also provided with the HPF task library (see section 10.3. So the routines in the local model have the same syntax as the corresponding routines for communication between data parallel tasks.


K..2 HPF_SERIAL Procedures

K..2.1 Example for Serial Extrinsics

In some situations it is necessary that only one node calls a certain subroutine, e.g. for X-Windows routines.

      interface
 
         extrinsic (hpf_serial) subroutine x_display_init (width, height)
         integer width, height
         intent (in) :: width, height
         end
 
         extrinsic (hpf_serial) subroutine x_show_image (image, width, height)
         integer image (height, width)
         integer height, width
         intent (in) :: width, height, image
         end subroutine
 
         extrinsic (hpf_serial) subroutine x_new_action (hx1, hx2, hy1, hy2)
         integer hx1, hx2, hy1, hy2
         intent (inout) :: hx1, hx2, hy1, hy2     ! default is in-out
         end
 
         extrinsic (hpf_serial) subroutine x_display_exit
         end
 
      end interface

K..2.2 Invoking a Serial Routine

A serial routine will always be called by a single processor only. The compiler generates communication to make sure that all parameter data is available on this processor. A serial procedure can also be called with distributed data. In this case, the calling routine will generate an incarnation of the full array on the node that will call the subroutine. After the call of the serial procedure all replicated data will be broadcast and the distributed data will be restored. Information about the intent of the arguments will be used to decide about the necessity.

Usually, a serial procedure will be executed by the first processor that executes also all I/O routines (in this sense I/O operations are very similar to serial routines). But if all are arguments are distributed on one processor, that processor will run the call.

      real A(N), B(N)
!hpf$ distribute (block) :: A, B
      ...
      call SERIAL (A(I), B(I))   ! will be executed by owner of A(I), B(I)

In this example, the routine SERIAL runs on the processor that owns A(I) and B(I). If such a call is within a loop and at each iteration a different processor is used, efficient parallelism is given.

K..2.3 Interface for HPF_SERIAL Routines

Attention: An interface block is usually mandatory to guarantee in the calling routine that the routine is executed on a single processor. Only if the user specifies a home for the subroutine call that corresponds to a single processor and if the compiler accepts it, it is not necessary.

In a certain sense, a serial routine corresponds to a data parallel routine that is executed on a single processor. The calling routine has to guarantee the locality of the arguments.

K..2.4 Execution of HPF_SERIAL Routines

As a serial routine is always executed on a single processor, the HPF compiler has not to generate any communication. All actual arguments are mapped to or have been mapped to the processor executing the routine. Local variables become private variables.

K..2.5 Access to Global Data in Serial Routines

The HPF standard does not allow to share global data (e.g. COMMON blocks) between serial and global HPF routines, for many good reasons. If global data is updated in a serial routine on a single processor, this might result in inconsistencies. On the other hand, it is very useful to read replicated global data in the serial routine. This is supported within ADAPTOR.

      real A(N), B(N)        ! replicated data 
      common /DATA/ A, B
      read *, A, B
      ...
      call SERIAL ()   ! will be executed by one processor
      ...

      extrinsic (HPF_SERIAL) subroutine SERIAL ()
      real A(N), B(N), X
      common /DATA/ A, B
      X = A(5)          ! might be useful
      A(3) = X          ! not HPF conform as only one processor updates
      ...
      end subroutine SERIAL

Furthermore, ADAPTOR will also generate code when global distributed data is accessed. Again, the user is responsible that the serial routine only accesses data that is local on the executing processor. This corresponds to the access of global data in a data parallel routine that is only executed on a subset of processors.

       module DATA
       integer, paramter :: N = 100
       real, dimension (N, N) :: A
!hpf$  distribute A(*,block)
       end module DATA

       program WORK
       use DATA
       ...
!hpf$  independent, on home (A(:,I))
       do I = 1, N
          call WORK_COL (I)
       end do
       ...
       end program WORK

       extrinsic (HPF_SERIAL) subroutine WORK_COL (I)
       use DATA
       integer I
       do K = 1, N
          A(I,g(K)) = f(A(I,h(K))
       end do
       end subroutine WORL_COL

As this example shows, the serial routine is used to take advantage of the fact that all data is resident when the routine is executed on the processor owning the i-th column of the distributed array A.

K..2.6 Library Access from Serial Extrinsics

Within a serial HPF program, all HPF_LIBRARY routines can be called. The HPF_LOCAL_LIBRARY module must not be used. Message passing within a serial routine is not useful as the routine is executed within a context that consists of a single processor.


K..3 F77_LOCAL Procedures

The main difference between a HPF_LOCAL and a F77_LOCAL routine is how arrays are passed. While in the HPF model usually both, pointers and HPF array descriptors (''handles''), are passed, the F77 routine will only expect one of them. This is simply due to the fact that HPF local routines will be compiled by the HPF compiler (knowing about descriptors) while F77 local routines are compiled by a FORTRAN 77 compiler.

If an HPF routine calls a local F77 routine, an interface must be available (exceptions for ADAPTOR are explained later).

If all of the following conditions are true, an interface is not necessary (at least for ADAPTOR):


K..4 F77_SERIAL Procedures

A F77 serial routine will be called only by one processor. The arguments itself are passed in the same way as for F77 local routines.

The inquiry subroutines for F77 local routines can also be called within serial F77 routines.


next up previous contents index
Next: L. HPF Intrinsic and Up: ADAPTOR HPF Language Reference Previous: J. Task Parallelism   Contents   Index
Thomas Brandes 2004-03-18