2 This is like ictest2.c, but it creates communictors that are valid only
3 at the "leaders"; other members of the local communicator are NOT
4 in the remote communicator. A peer communicator is constructed that
17 int main( int argc, char **argv )
19 int size, rank, key, lrank, rsize, result;
21 MPI_Comm mySecondComm;
22 MPI_Comm newComm, peerComm;
23 MPI_Group rgroup, lgroup, igroup;
24 int errors = 0, sum_errors;
29 MPI_Init ( &argc, &argv );
30 MPI_Comm_rank ( MPI_COMM_WORLD, &rank);
31 MPI_Comm_size ( MPI_COMM_WORLD, &size);
33 /* Only works for 2 or more processes */
35 We create an even and odd communicator, then create an
36 intercommunicator out of them. For this purpose, we use a
37 "peer" communicator valid only at one member of each of the odd and
41 MPI_Comm merge1, merge2, merge3, merge4;
43 /* Generate membership key in the range [0,1] */
45 /* Create the even communicator and odd communicators */
46 MPI_Comm_split ( MPI_COMM_WORLD, key, rank, &newComm );
48 MPI_Comm_test_inter( newComm, &flag );
51 printf( "[%d] got test_inter gave true for intra comm\n", rank );
54 /* Create the "peer" communicator */
56 if (rank < 2) key = 1;
57 MPI_Comm_split( MPI_COMM_WORLD, key, rank, &peerComm );
59 MPI_Comm_free( &peerComm );
63 MPI_Comm_rank( peerComm, &lrank );
64 printf( "[%d] lrank in peerComm is %d (color = %d, key=%d)\n",
65 rank, lrank, key, rank );
69 /* Check that the leader is who we think he is */
70 MPI_Comm_rank( newComm, &lrank );
71 /* printf( "[%d] local rank is %d\n", rank, lrank );
73 /* Perform the intercomm create and test it */
74 /* Local leader is always the one at rank 0. */
75 /* If even, the remote leader is rank 1, if odd, the remote leader
76 is rank 0 in the peercomm */
77 MPI_Intercomm_create (newComm, 0, peerComm, !(rank % 2), 1, &myFirstComm );
79 printf( "[%d] through intercom create\n", rank );
81 MPI_Barrier( MPI_COMM_WORLD );
82 printf( "[%d] through barrier at end of intercom create\n", rank );
84 MPI_Comm_test_inter( myFirstComm, &flag );
87 printf( "[%d] got test_inter gave false for inter comm\n", rank );
90 /* Try to dup this communicator */
91 MPI_Comm_dup ( myFirstComm, &mySecondComm );
92 MPI_Comm_test_inter( mySecondComm, &flag );
95 printf( "[%d] got test_inter gave false for dup of inter comm\n",
100 printf( "[%d] through comm dup\n", rank );
102 MPI_Barrier( MPI_COMM_WORLD );
103 printf( "[%d] through barrier at end of comm dup\n", rank );
106 /* Each member shares data with his "partner". */
107 MPI_Comm_rank( mySecondComm, &lrank );
108 MPI_Comm_remote_size( mySecondComm, &rsize );
111 printf( "[%d] lrank in secondcomm is %d and remote size is %d\n",
112 rank, lrank, rsize );
116 /* Check that the remote group is what we think */
117 MPI_Comm_remote_group( mySecondComm, &rgroup );
118 MPI_Comm_group( newComm, &lgroup );
119 MPI_Group_intersection( rgroup, lgroup, &igroup );
120 MPI_Group_compare( igroup, MPI_GROUP_EMPTY, &flag );
121 if (flag != MPI_IDENT) {
123 printf( "[%d] intersection of remote and local group is not empty\n",
126 MPI_Group_free( &rgroup );
127 MPI_Group_free( &lgroup );
128 MPI_Group_free( &igroup );
130 /* Send key * size + rank in communicator */
134 myval = key * size + lrank;
137 printf( "[%d] exchanging %d with %d in intercomm\n",
138 rank, myval, lrank );
141 MPI_Sendrecv (&myval, 1, MPI_INT, lrank, 0,
142 &hisval, 1, MPI_INT, lrank, 0, mySecondComm, &status);
143 if (hisval != (lrank + (!key)*size)) {
144 printf( "[%d] expected %d but got %d\n", rank, lrank + (!key)*size,
151 printf("[%d] Failed!\n",rank);
153 /* Key is 1 for oddComm, 0 for evenComm (note both contain 0 in WORLD) */
155 printf( "[%d] starting intercom merge\n", rank );
158 MPI_Intercomm_merge ( mySecondComm, key, &merge1 );
159 MPI_Intercomm_merge ( mySecondComm, (key+1)%2, &merge2 );
160 MPI_Intercomm_merge ( mySecondComm, 0, &merge3 );
161 MPI_Intercomm_merge ( mySecondComm, 1, &merge4 );
163 MPI_Comm_compare( merge1, MPI_COMM_WORLD, &result );
164 if (result != MPI_SIMILAR && size > 2) {
165 printf( "[%d] comparision with merge1 failed\n", rank );
169 /* Free communicators */
170 if (verbose) printf( "about to free communicators\n" );
171 MPI_Comm_free( &newComm );
172 if (peerComm != MPI_COMM_NULL) MPI_Comm_free( &peerComm );
173 MPI_Comm_free( &myFirstComm );
174 MPI_Comm_free( &mySecondComm );
175 MPI_Comm_free( &merge1 );
176 MPI_Comm_free( &merge2 );
177 MPI_Comm_free( &merge3 );
178 MPI_Comm_free( &merge4 );
181 printf("[%d] Failed - at least 2 nodes must be used\n",rank);
183 MPI_Barrier( MPI_COMM_WORLD );
184 MPI_Allreduce( &errors, &sum_errors, 1, MPI_INT, MPI_SUM, MPI_COMM_WORLD );
185 if (sum_errors > 0) {
186 printf( "%d errors on process %d\n", errors, rank );
188 else if (rank == 0) {
189 printf( " No Errors\n" );
191 /* Finalize and end! */