Logo AND Algorithmique Numérique Distribuée

Public GIT Repository
Reduce the size of partial shared malloc tests.
[simgrid.git] / teshsuite / smpi / mpich3-test / rma / atomic_get.c
1 /* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil ; -*- */
2 /*
3  *  (C) 2015 by Argonne National Laboratory.
4  *      See COPYRIGHT in top-level directory.
5  */
6
7 /* This test is going to test atomic GET (GACC/FOP+MPI_NO_OP).
8  *
9  * There are totally three processes involved in this test. Both
10  * rank 1 and rank 2 issue RMA operations to rank 0. Rank 2 issues
11  * atomic PUT (ACC+MPI_REPLACE), whereas rank 1 issues atomic
12  * GET (GACC/FOP+MPI_NO_OP). The datatype used in the test is
13  * pair-type. The initial value of pair-type data in origin buffer
14  * of atomic PUT is set so that the two basic values equal with
15  * each other. Due to the atomicity of GET, the expected resulting
16  * data should also have equivalent basic values. */
17
18 #include "mpi.h"
19 #include <stdio.h>
20
21 #define LOOP 100
22 #define DATA_SIZE 100
23 #define OPS_NUM 10000
24 #define GACC_SZ 10
25
26 typedef struct pair_struct {
27     long double a;
28     int b;
29 } pair_struct_t;
30
31 int main(int argc, char *argv[])
32 {
33     int rank, nproc;
34     int i, j, k;
35     int errors = 0, curr_errors = 0;
36     MPI_Win win;
37     pair_struct_t *tar_buf = NULL;
38     pair_struct_t *orig_buf = NULL;
39     pair_struct_t *result_buf = NULL;
40
41     /* This test needs to work with 3 processes. */
42
43     MPI_Init(&argc, &argv);
44
45     MPI_Comm_size(MPI_COMM_WORLD, &nproc);
46     MPI_Comm_rank(MPI_COMM_WORLD, &rank);
47
48     MPI_Alloc_mem(sizeof(pair_struct_t) * DATA_SIZE, MPI_INFO_NULL, &orig_buf);
49     MPI_Alloc_mem(sizeof(pair_struct_t) * DATA_SIZE, MPI_INFO_NULL, &result_buf);
50
51     MPI_Win_allocate(sizeof(pair_struct_t) * DATA_SIZE, sizeof(pair_struct_t),
52                      MPI_INFO_NULL, MPI_COMM_WORLD, &tar_buf, &win);
53
54     for (j = 0; j < LOOP * 6; j++) {
55
56         MPI_Win_lock(MPI_LOCK_EXCLUSIVE, rank, 0, win);
57
58         /* initialize data */
59         for (i = 0; i < DATA_SIZE; i++) {
60             tar_buf[i].a = 0.0;
61             tar_buf[i].b = 0;
62             result_buf[i].a = 0.0;
63             result_buf[i].b = 0;
64         }
65
66         MPI_Win_unlock(rank, win);
67
68         MPI_Barrier(MPI_COMM_WORLD);
69
70         MPI_Win_fence(0, win);
71
72         if (rank == 2) {
73             if (j < 2 * LOOP) {
74                 /* Work with FOP test (Test #1 to Test #2) */
75                 for (i = 0; i < OPS_NUM; i++) {
76
77                     int curr_val = j * OPS_NUM + i;
78                     orig_buf[0].a = (long double) (curr_val);
79                     orig_buf[0].b = curr_val;
80
81                     MPI_Accumulate(orig_buf, 1, MPI_LONG_DOUBLE_INT,
82                                    0, 0, 1, MPI_LONG_DOUBLE_INT, MPI_REPLACE, win);
83                 }
84             }
85             else {
86                 /* Work with GACC test (Test #3 to Test #6) */
87                 for (i = 0; i < OPS_NUM / GACC_SZ; i++) {
88
89                     for (k = 0; k < GACC_SZ; k++) {
90                         int curr_val = j * OPS_NUM + i * GACC_SZ + k;
91                         orig_buf[k].a = (long double) (curr_val);
92                         orig_buf[k].b = curr_val;
93                     }
94
95                     MPI_Accumulate(orig_buf, GACC_SZ, MPI_LONG_DOUBLE_INT,
96                                    0, 0, GACC_SZ, MPI_LONG_DOUBLE_INT, MPI_REPLACE, win);
97                 }
98             }
99         }
100         else if (rank == 1) {
101             /* equals to an atomic GET */
102             if (j < LOOP) {
103                 for (i = 0; i < DATA_SIZE; i++) {
104                     /* Test #1: FOP + MPI_NO_OP */
105                     MPI_Fetch_and_op(orig_buf, &(result_buf[i]), MPI_LONG_DOUBLE_INT,
106                                      0, 0, MPI_NO_OP, win);
107                 }
108             }
109             else if (j < 2 * LOOP) {
110                 for (i = 0; i < DATA_SIZE; i++) {
111                     /* Test #2: FOP + MPI_NO_OP + NULL origin buffer address */
112                     MPI_Fetch_and_op(NULL, &(result_buf[i]), MPI_LONG_DOUBLE_INT,
113                                      0, 0, MPI_NO_OP, win);
114                 }
115             }
116             else if (j < 3 * LOOP) {
117                 for (i = 0; i < DATA_SIZE / GACC_SZ; i++) {
118                     /* Test #3: GACC + MPI_NO_OP */
119                     MPI_Get_accumulate(orig_buf, GACC_SZ, MPI_LONG_DOUBLE_INT,
120                                        &(result_buf[i * GACC_SZ]), GACC_SZ, MPI_LONG_DOUBLE_INT,
121                                        0, 0, GACC_SZ, MPI_LONG_DOUBLE_INT, MPI_NO_OP, win);
122                 }
123             }
124             else if (j < 4 * LOOP) {
125                 for (i = 0; i < DATA_SIZE / GACC_SZ; i++) {
126                     /* Test #4: GACC + MPI_NO_OP + NULL origin buffer address */
127                     MPI_Get_accumulate(NULL, GACC_SZ, MPI_LONG_DOUBLE_INT,
128                                        &(result_buf[i * GACC_SZ]), GACC_SZ, MPI_LONG_DOUBLE_INT,
129                                        0, 0, GACC_SZ, MPI_LONG_DOUBLE_INT, MPI_NO_OP, win);
130                 }
131             }
132             else if (j < 5 * LOOP) {
133                 for (i = 0; i < DATA_SIZE / GACC_SZ; i++) {
134                     /* Test #5: GACC + MPI_NO_OP + zero origin count */
135                     MPI_Get_accumulate(orig_buf, 0, MPI_LONG_DOUBLE_INT,
136                                        &(result_buf[i * GACC_SZ]), GACC_SZ, MPI_LONG_DOUBLE_INT,
137                                        0, 0, GACC_SZ, MPI_LONG_DOUBLE_INT, MPI_NO_OP, win);
138                 }
139             }
140             else if (j < 6 * LOOP) {
141                 for (i = 0; i < DATA_SIZE / GACC_SZ; i++) {
142                     /* Test #5: GACC + MPI_NO_OP + NULL origin datatype */
143                     MPI_Get_accumulate(orig_buf, GACC_SZ, MPI_DATATYPE_NULL,
144                                        &(result_buf[i * GACC_SZ]), GACC_SZ, MPI_LONG_DOUBLE_INT,
145                                        0, 0, GACC_SZ, MPI_LONG_DOUBLE_INT, MPI_NO_OP, win);
146                 }
147             }
148         }
149
150         MPI_Win_fence(0, win);
151
152         /* check results */
153         if (rank == 1) {
154             for (i = 0; i < DATA_SIZE; i++) {
155                 if (result_buf[i].a != (long double) (result_buf[i].b)) {
156                     if (curr_errors < 10) {
157                         printf("LOOP %d: result_buf[%d].a = %Lf, result_buf[%d].b = %d\n",
158                                j, i, result_buf[i].a, i, result_buf[i].b);
159                     }
160                     curr_errors++;
161                 }
162             }
163         }
164
165         if (j % LOOP == 0) {
166             errors += curr_errors;
167             curr_errors = 0;
168         }
169     }
170
171     MPI_Win_free(&win);
172
173     MPI_Free_mem(orig_buf);
174     MPI_Free_mem(result_buf);
175
176     if (rank == 1) {
177         if (errors == 0)
178             printf(" No Errors\n");
179     }
180
181     MPI_Finalize();
182     return 0;
183 }