Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
ИНСАЙД ИНФА MPI.pdf
Скачиваний:
15
Добавлен:
15.04.2015
Размер:
3.3 Mб
Скачать

6.6. INTER-COMMUNICATION

221

Group 0

Group 1

Group 2

Figure 6.3: Three-group pipeline.

LOGICAL HIGH

fMPI::Intracomm MPI::Intercomm::Merge(bool high) const (binding deprecated, see Section 15.2) g

This function creates an intra-communicator from the union of the two groups that are associated with intercomm. All processes should provide the same high value within each of the two groups. If processes in one group provided the value high = false and processes in the other group provided the value high = true then the union orders the \low" group before the \high" group. If all processes provided the same high argument then the order of the union is arbitrary. This call is blocking and collective within the union of the two groups.

The error handler on the new intercommunicator in each process is inherited from the communicator that contributes the local group. Note that this can result in di erent processes in the same communicator having di erent error handlers.

Advice to implementors. The implementation of MPI_INTERCOMM_MERGE,

MPI_COMM_FREE and MPI_COMM_DUP are similar to the implementation of MPI_INTERCOMM_CREATE, except that contexts private to the input inter-com- municator are used for communication between group leaders rather than contexts inside a bridge communicator. (End of advice to implementors.)

6.6.3 Inter-Communication Examples

Example 1: Three-Group \Pipeline"

Groups 0 and 1 communicate. Groups 1 and 2 communicate. Therefore, group 0 requires one inter-communicator, group 1 requires two inter-communicators, and group 2 requires 1 inter-communicator.

int main(int

argc, char **argv)

{

 

 

 

MPI_Comm

myComm;

/* intra-communicator of local sub-group */

MPI_Comm

myFirstComm;

/*

inter-communicator */

MPI_Comm

mySecondComm; /*

second inter-communicator (group 1 only) */

int membershipKey; int rank;

MPI_Init(&argc, &argv);

MPI_Comm_rank(MPI_COMM_WORLD, &rank);

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

34

35

36

37

38

39

40

41

42

43

44

45

46

47

48

222 CHAPTER 6. GROUPS, CONTEXTS, COMMUNICATORS, AND CACHING

1/* User code must generate membershipKey in the range [0, 1, 2] */

2

3

membershipKey = rank % 3;

4/* Build intra-communicator for local sub-group */

5MPI_Comm_split(MPI_COMM_WORLD, membershipKey, rank, &myComm);

6

7/* Build inter-communicators. Tags are hard-coded. */

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

if (membershipKey == 0)

 

 

{

/* Group 0 communicates with

group 1. */

 

MPI_Intercomm_create(

myComm, 0, MPI_COMM_WORLD,

1,

 

 

1, &myFirstComm);

 

}

 

 

 

else if (membershipKey == 1)

 

{

/* Group

1 communicates with groups

0 and 2. */

 

MPI_Intercomm_create(

myComm, 0, MPI_COMM_WORLD,

0,

 

 

1, &myFirstComm);

 

 

MPI_Intercomm_create(

myComm, 0, MPI_COMM_WORLD,

2,

 

 

12, &mySecondComm);

 

}

 

 

 

else if (membershipKey == 2)

 

{

/* Group 2 communicates with

group 1. */

 

MPI_Intercomm_create(

myComm, 0, MPI_COMM_WORLD,

1,

 

 

12, &myFirstComm);

 

}

 

 

 

/* Do work ... */

28switch(membershipKey) /* free communicators appropriately */

29{

30case 1:

31MPI_Comm_free(&mySecondComm);

32case 0:

33case 2:

34MPI_Comm_free(&myFirstComm);

35break;

36}

37

38

39

40

41

MPI_Finalize();

}

42 Example 2: Three-Group \Ring"

43

Groups 0 and 1 communicate. Groups 1 and 2 communicate. Groups 0 and 2 communicate.

44

Therefore, each requires two inter-communicators.

45

46

47

48

int main(int argc, char **argv)

{

MPI_Comm

myComm;

/* intra-communicator of local sub-group */

6.6. INTER-COMMUNICATION

223

Group 0

Group 1

Group 2

 

Figure 6.4: Three-group ring.

MPI_Comm

myFirstComm; /* inter-communicators */

MPI_Comm

mySecondComm;

MPI_Status

status;

int membershipKey; int rank;

MPI_Init(&argc, &argv);

MPI_Comm_rank(MPI_COMM_WORLD, &rank);

...

/* User code must generate membershipKey in the range [0, 1, 2] */ membershipKey = rank % 3;

/* Build intra-communicator for local sub-group */ MPI_Comm_split(MPI_COMM_WORLD, membershipKey, rank, &myComm);

/* Build inter-communicators. Tags are hard-coded. */ if (membershipKey == 0)

{

/* Group 0 communicates with groups 1 and 2. */

 

MPI_Intercomm_create(

myComm,

0,

MPI_COMM_WORLD, 1,

 

 

1, &myFirstComm);

 

MPI_Intercomm_create(

myComm,

0,

MPI_COMM_WORLD, 2,

 

 

2, &mySecondComm);

}

else if (membershipKey == 1)

{ /* Group 1 communicates with groups 0 and 2. */ MPI_Intercomm_create( myComm, 0, MPI_COMM_WORLD, 0,

1, &myFirstComm); MPI_Intercomm_create( myComm, 0, MPI_COMM_WORLD, 2,

12, &mySecondComm);

}

else if (membershipKey == 2)

{ /* Group 2 communicates with groups 0 and 1. */ MPI_Intercomm_create( myComm, 0, MPI_COMM_WORLD, 0,

2, &myFirstComm); MPI_Intercomm_create( myComm, 0, MPI_COMM_WORLD, 1,

12, &mySecondComm);

}

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

34

35

36

37

38

39

40

41

42

43

44

45

46

47

48