Let us consider the ways in which this interface might operate:
Let us first consider case a. A pC++ element class which contains three arrays with two of the arrays being a special type FArrayDouble and one being a conventional C++ array is given below.
class MyElement {
public:
FArrayDouble x, y;
double z[100];
MyElement();
};
The special type FArrayDouble is used to contain double precision
Fortran90 arrays and their descriptor structures.
To define the constructor for the class we assume that x is a one
dimensional array of a size of 100 and y
is a two dimensional array of a size of
MyElement::MyElement():x(100),y(200,50)
{...}
To use this class in a pC++ program that calls an HPF subroutine,
we need to define the Processors object and to specify the size and
shape of the collection. In the following example, a one dimensional
collection
of a size of 64 with elements of type MyElement is constructed
and an HPF subroutine, FFUN, is called.
extern "HPF" void FFUN(FArrayDouble&,
FArrayDouble&,double*);
main(){
Processors P(64);
Distribution D(64,&P,BLOCK);
Align A(64,"[ALIGN(T[i],D[i])]");
HPFCollection<MyElement> C(&D,&A);
FFUN(C.x,C.y,C.z);
...
}
The important point to consider is what the passed arguments look like
in terms of HPF distributed arrays.
In this case, they can be defined by the HPF directives.
!HPF$ PROCESSORS P(64)
double precision x(100*64),
& y(200*64,50),z(100*64)
!HPF$ DISTRIBUTE x(BLOCK),y(BLOCK,*) ONTO P
!HPF$ DISTRIBUTE z(BLOCK) ONTO P
It is relatively easy to see how the blocked decomposition corresponds to our
simple collection of array blocks. When we have a two dimensional
array of virtual processors, we would have a pC++ program as below:
main(){
Processors P(64,32);
Distribution D(64,32,&P,BLOCK,BLOCK);
Align A(64,32,"[ALIGN(T[i][j],D[i][j])]");
HPFCollection<MyElement> C(&D,&A);
FFUN(C.x,C.y,C.z);
...
}
In this case, the HPF function would see these structures as defined by the
following sequence of directives.
!HPF$ PROCESSORS P(64,32)
double precision x(100*64,32),
& y(200*64, 50*32),z(100*64,32)
!HPF$ DISTRIBUTE x(BLOCK,BLOCK) ONTO P
!HPF$ DISTRIBUTE y(BLOCK,BLOCK) ONTO P
!HPF$ DISTRIBUTE z(BLOCK,BLOCK) ONTO P
The reader will note that we have not described how to create arrays that
are distributed with anything other than a BLOCK distribution
and array sizes are restricted to be multiples of the processor array size.
There are ways around these restrictions, but they will not be discussed here.