34 #ifndef conv_tools_hpp 35 #define conv_tools_hpp 42 #include <communicate.hpp> 43 #include <settings.hpp> 52 namespace conv_tools {
55 template <
typename ValueType,
typename IndexType>
56 void put_all_local_residual_norms(
58 ValueType &local_resnorm,
59 std::shared_ptr<gko::matrix::Dense<ValueType>> &local_residual_vector,
60 MPI_Win &window_residual_vector)
63 auto my_rank = metadata.
my_rank;
64 auto l_res_vec = local_residual_vector->get_values();
66 auto mpi_vtype = schwz::mpi::get_mpi_datatype(l_res_vec[my_rank]);
68 l_res_vec[my_rank] = std::min(l_res_vec[my_rank], local_resnorm);
69 for (
auto j = 0; j < num_subdomains; j++) {
71 metadata.post_process_data.global_residual_vector_out[my_rank];
72 if (j != my_rank && iter > 0 && l_res_vec[my_rank] != gres[iter - 1]) {
73 MPI_Put(&l_res_vec[my_rank], 1, mpi_vtype, j, my_rank, 1, mpi_vtype,
74 window_residual_vector);
76 MPI_Win_flush(j, window_residual_vector);
78 MPI_Win_flush_local(j, window_residual_vector);
85 template <
typename ValueType,
typename IndexType,
typename MixedValueType>
86 void propagate_all_local_residual_norms(
90 ValueType &local_resnorm,
91 std::shared_ptr<gko::matrix::Dense<ValueType>> &local_residual_vector,
92 MPI_Win &window_residual_vector)
95 auto my_rank = metadata.
my_rank;
96 auto l_res_vec = local_residual_vector->get_values();
98 auto global_put = comm_s.
global_put->get_data();
100 auto max_valtype = std::numeric_limits<ValueType>::max();
101 auto mpi_vtype = schwz::mpi::get_mpi_datatype(l_res_vec[my_rank]);
103 l_res_vec[my_rank] = std::min(l_res_vec[my_rank], local_resnorm);
104 auto gres = metadata.post_process_data.global_residual_vector_out[my_rank];
106 if ((global_put[i])[0] > 0) {
107 auto p = neighbors_out[i];
109 if (iter == 0 || l_res_vec[my_rank] != gres[iter - 1]) flag = 1;
111 for (
auto j = 0; j < num_subdomains; j++) {
112 if (j != p && iter > 0 && l_res_vec[j] != max_valtype &&
114 (metadata.post_process_data
115 .global_residual_vector_out[j])[iter - 1]) {
121 for (
auto j = 0; j < num_subdomains; j++) {
123 (iter == 0 || l_res_vec[my_rank] != gres[iter - 1])) ||
124 (j != p && iter > 0 && l_res_vec[j] != max_valtype &&
126 (metadata.post_process_data
127 .global_residual_vector_out[j])[iter - 1])) {
129 MPI_Accumulate(&l_res_vec[j], 1, mpi_vtype, p, j, 1,
131 window_residual_vector);
135 MPI_Win_flush(p, window_residual_vector);
137 MPI_Win_flush_local(p, window_residual_vector);
146 template <
typename ValueType,
typename IndexType>
147 void global_convergence_check_onesided_tree(
149 std::shared_ptr<gko::Array<IndexType>> &convergence_vector,
150 int &converged_all_local,
int &num_converged_procs,
151 MPI_Win &window_convergence)
155 auto my_rank = metadata.
my_rank;
156 auto conv_vector = convergence_vector->get_data();
160 if (((conv_vector[0] == 1 &&
161 conv_vector[1] == 1) ||
162 (conv_vector[0] == 1 &&
163 my_rank == num_subdomains / 2 - 1) ||
164 (my_rank >= num_subdomains / 2 && conv_vector[0] != 2)) &&
165 converged_all_local > 0)
172 int p = (my_rank - 1) / 2;
173 int id = (my_rank % 2 == 0 ? 1 : 0);
174 MPI_Put(&ione, 1, MPI_INT, p,
id, 1, MPI_INT, window_convergence);
176 MPI_Win_flush(p, window_convergence);
178 MPI_Win_flush_local(p, window_convergence);
185 if (conv_vector[2] == 1) {
186 int p = 2 * my_rank + 1;
187 if (p < num_subdomains) {
188 MPI_Put(&ione, 1, MPI_INT, p, 2, 1, MPI_INT, window_convergence);
190 MPI_Win_flush(p, window_convergence);
192 MPI_Win_flush_local(p, window_convergence);
196 if (p < num_subdomains) {
197 MPI_Put(&ione, 1, MPI_INT, p, 2, 1, MPI_INT, window_convergence);
199 MPI_Win_flush(p, window_convergence);
201 MPI_Win_flush_local(p, window_convergence);
205 num_converged_procs = num_subdomains;
207 num_converged_procs = 0;
212 template <
typename ValueType,
typename IndexType,
typename MixedValueType>
213 void global_convergence_decentralized(
217 std::shared_ptr<gko::Array<IndexType>> &convergence_vector,
218 std::shared_ptr<gko::Array<IndexType>> &convergence_sent,
219 std::shared_ptr<gko::Array<IndexType>> &convergence_local,
220 int &converged_all_local,
int &num_converged_procs,
221 MPI_Win &window_convergence)
224 auto my_rank = metadata.
my_rank;
225 auto conv_vector = convergence_vector->get_data();
226 auto conv_sent = convergence_sent->get_data();
227 auto conv_local = convergence_local->get_data();
228 auto global_put = comm_s.
global_put->get_data();
230 if (settings.convergence_settings.enable_accumulate) {
231 if (converged_all_local == 1) {
232 for (
auto j = 0; j < num_subdomains; j++) {
235 MPI_Accumulate(&ione, 1, MPI_INT, j, 0, 1, MPI_INT, MPI_SUM,
238 MPI_Win_flush(j, window_convergence);
240 MPI_Win_flush_local(j, window_convergence);
247 num_converged_procs = conv_vector[0];
249 if (converged_all_local == 1) {
250 conv_vector[my_rank] = 1;
252 num_converged_procs = 0;
253 std::copy(conv_vector, conv_vector + num_subdomains, conv_local);
254 num_converged_procs =
255 std::accumulate(conv_vector, conv_vector + num_subdomains, 0);
257 if ((global_put[i])[0] > 0) {
258 auto p = neighbors_out[i];
260 for (
auto j = 0; j < num_subdomains; j++) {
261 if (conv_sent[j] == 0 && conv_local[j] == 1) {
262 MPI_Put(&ione, 1, MPI_INT, p, j, 1, MPI_INT,
267 MPI_Win_flush(p, window_convergence);
269 MPI_Win_flush_local(p, window_convergence);
273 std::copy(conv_local, conv_local + num_subdomains, conv_sent);
319 #endif // conv_tools.hpp bool enable_flush_local
Use local flush.
Definition: settings.hpp:251
std::shared_ptr< gko::Array< IndexType > > neighbors_out
The neighbors this subdomain has to send data to.
Definition: communicate.hpp:87
The communication struct used to store the communication data.
Definition: communicate.hpp:67
std::shared_ptr< gko::Array< IndexType * > > global_put
The array containing the number of elements that each subdomain sends from the other.
Definition: communicate.hpp:120
int num_neighbors_out
The number of neighbors this subdomain has to send data to.
Definition: communicate.hpp:77
The struct that contains the solver settings and the parameters to be set by the user.
Definition: settings.hpp:77
The Schwarz wrappers namespace.
Definition: comm_helpers.hpp:49
bool enable_flush_all
Use flush all.
Definition: settings.hpp:256