GCC Code Coverage Report


Directory: ./
File: tasks/volkov_a_odd_even_transposition/mpi/src/ops_mpi.cpp
Date: 2026-01-10 02:40:41
Exec Total Coverage
Lines: 61 66 92.4%
Functions: 6 8 75.0%
Branches: 35 66 53.0%

Line Branch Exec Source
1 #include "volkov_a_odd_even_transposition/mpi/include/ops_mpi.hpp"
2
3 #include <mpi.h>
4
5 #include <algorithm>
6 #include <vector>
7
8 #include "volkov_a_odd_even_transposition/common/include/common.hpp"
9
10 namespace volkov_a_odd_even_transposition {
11
12
1/2
✓ Branch 1 taken 12 times.
✗ Branch 2 not taken.
12 OddEvenSortMPI::OddEvenSortMPI(const InType &in) {
13 SetTypeOfTask(GetStaticTypeOfTask());
14
1/2
✓ Branch 1 taken 12 times.
✗ Branch 2 not taken.
12 GetInput() = in;
15 12 }
16
17 12 bool OddEvenSortMPI::ValidationImpl() {
18 12 int rank = 0;
19 12 MPI_Comm_rank(MPI_COMM_WORLD, &rank);
20
2/2
✓ Branch 0 taken 6 times.
✓ Branch 1 taken 6 times.
12 if (rank == 0) {
21 6 return GetOutput().empty();
22 }
23 return true;
24 }
25
26 12 bool OddEvenSortMPI::PreProcessingImpl() {
27 12 int rank = 0;
28 12 MPI_Comm_rank(MPI_COMM_WORLD, &rank);
29
2/2
✓ Branch 0 taken 6 times.
✓ Branch 1 taken 6 times.
12 if (rank == 0) {
30 6 GetOutput().resize(GetInput().size());
31 }
32 12 return true;
33 }
34
35 void OddEvenSortMPI::CalculateDistribution(int n, int size, std::vector<int> &counts, std::vector<int> &displs) {
36 12 int rem = n % size;
37 12 int base = n / size;
38 int offset = 0;
39
40
2/4
✓ Branch 0 taken 24 times.
✓ Branch 1 taken 12 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
36 for (int i = 0; i < size; ++i) {
41
2/4
✓ Branch 0 taken 22 times.
✓ Branch 1 taken 2 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
46 counts[i] = base + (i < rem ? 1 : 0);
42 24 displs[i] = offset;
43 24 offset += counts[i];
44 }
45 }
46
47 12 void OddEvenSortMPI::PerformCompareSplit(InType &local_data, int partner_rank, int my_rank) {
48 12 int my_count = static_cast<int>(local_data.size());
49 12 int partner_count = 0;
50
51 12 MPI_Sendrecv(&my_count, 1, MPI_INT, partner_rank, 0, &partner_count, 1, MPI_INT, partner_rank, 0, MPI_COMM_WORLD,
52 MPI_STATUS_IGNORE);
53
54 12 InType partner_data(partner_count);
55
56
1/2
✓ Branch 1 taken 12 times.
✗ Branch 2 not taken.
12 MPI_Sendrecv(local_data.data(), my_count, MPI_INT, partner_rank, 1, partner_data.data(), partner_count, MPI_INT,
57 partner_rank, 1, MPI_COMM_WORLD, MPI_STATUS_IGNORE);
58
59
1/4
✓ Branch 1 taken 12 times.
✗ Branch 2 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
12 InType merged(my_count + partner_count);
60
61 12 std::ranges::merge(local_data, partner_data, merged.begin());
62
63
2/2
✓ Branch 0 taken 6 times.
✓ Branch 1 taken 6 times.
12 if (my_rank < partner_rank) {
64
1/2
✓ Branch 1 taken 6 times.
✗ Branch 2 not taken.
6 local_data.assign(merged.begin(), merged.begin() + my_count);
65 } else {
66
1/2
✓ Branch 1 taken 6 times.
✗ Branch 2 not taken.
6 local_data.assign(merged.end() - my_count, merged.end());
67 }
68 12 }
69
70 int OddEvenSortMPI::GetNeighbor(int phase, int rank, int size) {
71 int partner = -1;
72 if (phase % 2 == 0) {
73
2/4
✓ Branch 0 taken 6 times.
✓ Branch 1 taken 6 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
12 if (rank % 2 == 0) {
74 6 partner = rank + 1;
75 } else {
76 6 partner = rank - 1;
77 }
78 } else {
79
2/4
✓ Branch 0 taken 6 times.
✓ Branch 1 taken 6 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
12 if (rank % 2 != 0) {
80 6 partner = rank + 1;
81 } else {
82 6 partner = rank - 1;
83 }
84 }
85
86
2/4
✓ Branch 0 taken 12 times.
✓ Branch 1 taken 12 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
24 if (partner < 0 || partner >= size) {
87 return -1;
88 }
89 return partner;
90 }
91
92 12 bool OddEvenSortMPI::RunImpl() {
93 12 int rank = 0;
94 12 int size = 0;
95 12 MPI_Comm_rank(MPI_COMM_WORLD, &rank);
96 12 MPI_Comm_size(MPI_COMM_WORLD, &size);
97
98 12 int n = 0;
99
2/2
✓ Branch 0 taken 6 times.
✓ Branch 1 taken 6 times.
12 if (rank == 0) {
100 6 n = static_cast<int>(GetInput().size());
101 }
102 12 MPI_Bcast(&n, 1, MPI_INT, 0, MPI_COMM_WORLD);
103
104 12 std::vector<int> counts(size);
105
1/4
✓ Branch 1 taken 12 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
12 std::vector<int> displs(size);
106 12 CalculateDistribution(n, size, counts, displs);
107
108
1/2
✓ Branch 1 taken 12 times.
✗ Branch 2 not taken.
12 int local_n = counts[rank];
109
2/6
✓ Branch 1 taken 12 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 12 times.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
12 InType local_vec(local_n);
110
111
1/2
✓ Branch 1 taken 12 times.
✗ Branch 2 not taken.
12 MPI_Scatterv(GetInput().data(), counts.data(), displs.data(), MPI_INT, local_vec.data(), local_n, MPI_INT, 0,
112 MPI_COMM_WORLD);
113
114 std::ranges::sort(local_vec);
115
116
2/2
✓ Branch 0 taken 24 times.
✓ Branch 1 taken 12 times.
36 for (int i = 0; i < size; ++i) {
117
2/2
✓ Branch 0 taken 12 times.
✓ Branch 1 taken 12 times.
24 int partner = GetNeighbor(i, rank, size);
118 if (partner != -1) {
119
1/2
✓ Branch 1 taken 12 times.
✗ Branch 2 not taken.
12 PerformCompareSplit(local_vec, partner, rank);
120 }
121 }
122
123
1/2
✓ Branch 1 taken 12 times.
✗ Branch 2 not taken.
12 MPI_Gatherv(local_vec.data(), local_n, MPI_INT, GetOutput().data(), counts.data(), displs.data(), MPI_INT, 0,
124 MPI_COMM_WORLD);
125
126 12 return true;
127 }
128
129 12 bool OddEvenSortMPI::PostProcessingImpl() {
130 12 return true;
131 }
132
133 } // namespace volkov_a_odd_even_transposition
134