1 /*
2 * Copyright (C) by Argonne National Laboratory
3 * See COPYRIGHT in top-level directory
4 */
5
6 #include <stdio.h>
7 #include <mpi.h>
8 #include "mpitest.h"
9 #include "mpithreadtest.h"
10
11 #define NUM_THREADS 8
12 #define NUM_ITER 100
13
14 #define check(X_) \
15 do { \
16 if (!(X_)) { \
17 printf("[%s:%d] -- Assertion failed: %s\n", __FILE__, __LINE__, #X_);\
18 MPI_Abort(MPI_COMM_WORLD, 1); \
19 } \
20 } while (0)
21
22 MPI_Comm comms[NUM_THREADS];
23 int rank, size;
24
test_comm_create(void * arg)25 MTEST_THREAD_RETURN_TYPE test_comm_create(void *arg)
26 {
27 int i;
28
29 for (i = 0; i < NUM_ITER; i++) {
30 MPI_Group world_group;
31 MPI_Comm comm;
32
33 MPI_Comm_group(comms[*(int *) arg], &world_group);
34
35 /* Every thread paticipates in a distinct MPI_Comm_create on distinct
36 * communicators. Thus, there is no violation of MPI threads +
37 * communicators semantics.
38 */
39
40 MPI_Comm_create(comms[*(int *) arg], world_group, &comm);
41 MPI_Barrier(comm);
42 MPI_Comm_free(&comm);
43
44 MPI_Group_free(&world_group);
45 }
46
47 return NULL;
48 }
49
50
main(int argc,char ** argv)51 int main(int argc, char **argv)
52 {
53 int thread_args[NUM_THREADS];
54 int i, err, provided;
55
56 MTest_Init_thread(&argc, &argv, MPI_THREAD_MULTIPLE, &provided);
57
58 check(provided == MPI_THREAD_MULTIPLE);
59
60 MPI_Comm_rank(MPI_COMM_WORLD, &rank);
61 MPI_Comm_size(MPI_COMM_WORLD, &size);
62
63 for (i = 0; i < NUM_THREADS; i++) {
64 MPI_Comm_dup(MPI_COMM_WORLD, &comms[i]);
65 }
66
67 for (i = 0; i < NUM_THREADS; i++) {
68 thread_args[i] = i;
69 MTest_Start_thread(test_comm_create, (void *) &thread_args[i]);
70 }
71
72 MTest_Join_threads();
73
74 for (i = 0; i < NUM_THREADS; i++) {
75 MPI_Comm_free(&comms[i]);
76 }
77
78 MTest_Finalize(0);
79
80 return 0;
81 }
82