ESPResSo
Extensible Simulation Package for Research on Soft Matter Systems
Loading...
Searching...
No Matches
LatticeWalberla.cpp
Go to the documentation of this file.
1/*
2 * Copyright (C) 2021-2023 The ESPResSo project
3 *
4 * This file is part of ESPResSo.
5 *
6 * ESPResSo is free software: you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation, either version 3 of the License, or
9 * (at your option) any later version.
10 *
11 * ESPResSo is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License
17 * along with this program. If not, see <http://www.gnu.org/licenses/>.
18 */
19
22
24
25#include <blockforest/Initialization.h>
26#include <blockforest/StructuredBlockForest.h>
27#include <core/DataTypes.h>
28#include <core/cell/Cell.h>
29#include <domain_decomposition/IBlock.h>
30
31#include <utils/Vector.hpp>
32
33#include <cmath>
34#include <initializer_list>
35#include <limits>
36#include <optional>
37#include <stdexcept>
38#include <string>
39#include <utility>
40
42 Utils::Vector3i const &node_grid,
43 unsigned int n_ghost_layers)
44 : m_grid_dimensions{grid_dimensions}, m_n_ghost_layers{n_ghost_layers} {
45 using walberla::real_t;
46 using walberla::uint_c;
47
48 for (auto const i : {0u, 1u, 2u}) {
49 if (m_grid_dimensions[i] % node_grid[i] != 0) {
50 throw std::runtime_error(
51 "Lattice grid dimensions and MPI node grid are not compatible.");
52 }
53 }
54
55 auto constexpr lattice_constant = real_t{1};
56 auto const cells_block = Utils::hadamard_division(grid_dimensions, node_grid);
57
58 m_blocks = walberla::blockforest::createUniformBlockGrid(
59 // number of blocks in each direction
60 uint_c(node_grid[0]), uint_c(node_grid[1]), uint_c(node_grid[2]),
61 // number of cells per block in each direction
62 uint_c(cells_block[0]), uint_c(cells_block[1]), uint_c(cells_block[2]),
63 lattice_constant,
64 // number of cpus per direction
65 uint_c(node_grid[0]), uint_c(node_grid[1]), uint_c(node_grid[2]),
66 // periodicity
67 true, true, true);
68 for (IBlock &block : *m_blocks) {
69 m_cached_blocks.push_back(&block);
70 }
71}
72
73[[nodiscard]] std::pair<Utils::Vector3d, Utils::Vector3d>
76 // We only have one block per mpi rank
77 assert(++(m_blocks->begin()) == m_blocks->end());
78
79 auto const ab = m_blocks->begin()->getAABB();
80 return {to_vector3d(ab.min()), to_vector3d(ab.max())};
81}
82
83[[nodiscard]] bool
85 // Note: Lattice constant =1, cell centers offset by .5
86 return ::walberla::get_block_and_cell(*this, node, false) != std::nullopt;
87}
88[[nodiscard]] bool
90 return ::walberla::get_block_and_cell(*this, node, true) != std::nullopt;
91}
92[[nodiscard]] bool
94 return ::walberla::get_block(*this, pos, false) != nullptr;
95}
96[[nodiscard]] bool
98 return ::walberla::get_block(*this, pos, true) != nullptr;
99}
100
101[[nodiscard]] Utils::Vector3i
103 double agrid) {
104 auto const grid_dimensions =
105 Utils::Vector3i{{static_cast<int>(std::round(box_size[0] / agrid)),
106 static_cast<int>(std::round(box_size[1] / agrid)),
107 static_cast<int>(std::round(box_size[2] / agrid))}};
108 for (auto const i : {0u, 1u, 2u}) {
109 if (std::abs(grid_dimensions[i] * agrid - box_size[i]) / box_size[i] >
110 std::numeric_limits<double>::epsilon()) {
111 throw std::runtime_error(
112 "Box length not commensurate with agrid in direction " +
113 std::to_string(i) + " length " + std::to_string(box_size[i]) +
114 " agrid " + std::to_string(agrid));
115 }
116 }
117 return grid_dimensions;
118}
Vector implementation and trait types for boost qvm interoperability.
bool pos_in_local_halo(Utils::Vector3d const &pos) const
static Utils::Vector3i calc_grid_dimensions(Utils::Vector3d const &box_size, double agrid)
bool node_in_local_halo(Utils::Vector3i const &node) const
std::pair< Utils::Vector3d, Utils::Vector3d > get_local_domain() const
LatticeWalberla(Utils::Vector3i const &grid_dimensions, Utils::Vector3i const &node_grid, unsigned int n_ghost_layers)
bool node_in_local_domain(Utils::Vector3i const &node) const
bool pos_in_local_domain(Utils::Vector3d const &pos) const
static double * block(double *p, std::size_t index, std::size_t size)
Definition elc.cpp:172
auto hadamard_division(Vector< T, N > const &a, Vector< U, N > const &b)
Definition Vector.hpp:422
Utils::Vector3d to_vector3d(Vector3< float > const &v)