1 /* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil ; -*- */
4 * (C) 2011 by Argonne National Laboratory.
5 * See COPYRIGHT in top-level directory.
14 #define RING_NUM_NEIGHBORS 2
16 static int validate_dgraph(MPI_Comm dgraph_comm)
21 int srcs[RING_NUM_NEIGHBORS], dests[RING_NUM_NEIGHBORS];
22 int *src_wgts, *dest_wgts;
24 int world_rank, world_size;
27 comm_topo = MPI_UNDEFINED;
28 MPI_Topo_test(dgraph_comm, &comm_topo);
33 fprintf(stderr, "dgraph_comm is NOT of type MPI_DIST_GRAPH\n");
37 ierr = MPI_Dist_graph_neighbors_count(dgraph_comm, &src_sz, &dest_sz, &wgt_flag);
38 if (ierr != MPI_SUCCESS) {
39 fprintf(stderr, "MPI_Dist_graph_neighbors_count() fails!\n");
44 fprintf(stderr, "MPI_Dist_graph_neighbors_count() succeeds!\n");
48 fprintf(stderr, "dgraph_comm is NOT created with MPI_UNWEIGHTED\n");
53 fprintf(stderr, "dgraph_comm is created with MPI_UNWEIGHTED\n");
55 if (src_sz != RING_NUM_NEIGHBORS || dest_sz != RING_NUM_NEIGHBORS) {
56 fprintf(stderr, "source or destination edge array is not of size %d.\n",
58 fprintf(stderr, "src_sz = %d, dest_sz = %d\n", src_sz, dest_sz);
63 * src_wgts and dest_wgts could be anything, e.g. NULL, since
64 * MPI_Dist_graph_neighbors_count() returns MPI_UNWEIGHTED.
65 * Since this program has a Fortran77 version, and standard Fortran77
66 * has no pointer and NULL, so use MPI_UNWEIGHTED for the weighted arrays.
68 src_wgts = MPI_UNWEIGHTED;
69 dest_wgts = MPI_UNWEIGHTED;
70 ierr = MPI_Dist_graph_neighbors(dgraph_comm, src_sz, srcs, src_wgts, dest_sz, dests, dest_wgts);
71 if (ierr != MPI_SUCCESS) {
72 fprintf(stderr, "MPI_Dist_graph_neighbors() fails!\n");
77 fprintf(stderr, "MPI_Dist_graph_neighbors() succeeds!\n");
81 * Check if the neighbors returned from MPI are really
82 * the nearest neighbors within a ring.
84 MPI_Comm_size(MPI_COMM_WORLD, &world_size);
85 MPI_Comm_rank(MPI_COMM_WORLD, &world_rank);
87 for (idx = 0; idx < src_sz; idx++) {
88 nbr_sep = abs(srcs[idx] - world_rank);
89 if (nbr_sep != 1 && nbr_sep != (world_size - 1)) {
90 fprintf(stderr, "srcs[%d]=%d is NOT a neighbor of my rank %d.\n",
91 idx, srcs[idx], world_rank);
95 for (idx = 0; idx < dest_sz; idx++) {
96 nbr_sep = abs(dests[idx] - world_rank);
97 if (nbr_sep != 1 && nbr_sep != (world_size - 1)) {
98 fprintf(stderr, "dests[%d]=%d is NOT a neighbor of my rank %d.\n",
99 idx, dests[idx], world_rank);
105 * fprintf(stderr, "dgraph_comm is of type MPI_DIST_GRAPH "
106 * "of a bidirectional ring.\n");
112 Specify a distributed graph of a bidirectional ring of the MPI_COMM_WORLD,
113 i.e. everyone only talks to left and right neighbors.
115 int main(int argc, char *argv[])
117 MPI_Comm dgraph_comm;
118 int world_size, world_rank, ierr;
123 int srcs[RING_NUM_NEIGHBORS], dests[RING_NUM_NEIGHBORS];
125 MTest_Init(&argc, &argv);
126 MPI_Comm_size(MPI_COMM_WORLD, &world_size);
127 MPI_Comm_rank(MPI_COMM_WORLD, &world_rank);
130 srcs[0] = world_rank;
131 dests[0] = world_rank - 1 < 0 ? world_size - 1 : world_rank - 1;
132 dests[1] = world_rank + 1 >= world_size ? 0 : world_rank + 1;
133 ierr = MPI_Dist_graph_create(MPI_COMM_WORLD, 1, srcs, degs, dests,
134 MPI_UNWEIGHTED, MPI_INFO_NULL, 1, &dgraph_comm);
135 if (ierr != MPI_SUCCESS) {
136 fprintf(stderr, "MPI_Dist_graph_create() fails!\n");
137 MPI_Abort(MPI_COMM_WORLD, 1);
140 if (!validate_dgraph(dgraph_comm)) {
141 fprintf(stderr, "MPI_Dist_graph_create() does NOT create " "a bidirectional ring graph!\n");
142 MPI_Abort(MPI_COMM_WORLD, 1);
145 MPI_Comm_free(&dgraph_comm);
148 srcs[0] = world_rank - 1 < 0 ? world_size - 1 : world_rank - 1;
149 srcs[1] = world_rank + 1 >= world_size ? 0 : world_rank + 1;
151 dests[0] = world_rank - 1 < 0 ? world_size - 1 : world_rank - 1;
152 dests[1] = world_rank + 1 >= world_size ? 0 : world_rank + 1;
153 ierr = MPI_Dist_graph_create_adjacent(MPI_COMM_WORLD,
154 src_sz, srcs, MPI_UNWEIGHTED,
155 dest_sz, dests, MPI_UNWEIGHTED,
156 MPI_INFO_NULL, 1, &dgraph_comm);
157 if (ierr != MPI_SUCCESS) {
158 fprintf(stderr, "MPI_Dist_graph_create_adjacent() fails!\n");
159 MPI_Abort(MPI_COMM_WORLD, 1);
162 if (!validate_dgraph(dgraph_comm)) {
163 fprintf(stderr, "MPI_Dist_graph_create_adjacent() does NOT create "
164 "a bidirectional ring graph!\n");
165 MPI_Abort(MPI_COMM_WORLD, 1);
168 MPI_Comm_free(&dgraph_comm);
170 MTest_Finalize(errs);