From f60b990ce6d962b6bef64b1a3f00f04a2a0b666a Mon Sep 17 00:00:00 2001 From: blegouix Date: Tue, 2 Apr 2024 19:58:08 +0200 Subject: [PATCH 001/189] init --- examples/characteristics_advection.cpp | 4 +- .../ddc/kernels/splines/spline_builder.hpp | 79 ++++---- .../ddc/kernels/splines/spline_builder_2d.hpp | 172 +++++++++++------- .../ddc/kernels/splines/spline_evaluator.hpp | 51 ++++-- .../kernels/splines/spline_evaluator_2d.hpp | 117 +++++++----- tests/splines/batched_2d_spline_builder.cpp | 2 +- tests/splines/batched_spline_builder.cpp | 2 +- tests/splines/extrapolation_rule.cpp | 2 +- tests/splines/periodicity_spline_builder.cpp | 2 +- 9 files changed, 262 insertions(+), 169 deletions(-) diff --git a/examples/characteristics_advection.cpp b/examples/characteristics_advection.cpp index e9a45d1f5..4e94b04fd 100644 --- a/examples/characteristics_advection.cpp +++ b/examples/characteristics_advection.cpp @@ -232,13 +232,13 @@ int main(int argc, char** argv) //! [instantiate intermediate chunks] // Instantiate chunk of spline coefs to receive output of spline_builder ddc::Chunk coef_alloc( - spline_builder.spline_domain(), + spline_builder.batched_spline_domain(), ddc::DeviceAllocator()); ddc::ChunkSpan coef = coef_alloc.span_view(); // Instantiate chunk to receive feet coords ddc::Chunk feet_coords_alloc( - spline_builder.vals_domain(), + spline_builder.batched_interpolation_domain(), ddc::DeviceAllocator>()); ddc::ChunkSpan feet_coords = feet_coords_alloc.span_view(); //! [instantiate intermediate chunks] diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index 2d2b33a04..0d841d492 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -78,7 +78,7 @@ class SplineBuilder */ using interpolation_domain_type = ddc::DiscreteDomain; - using vals_domain_type = ddc::DiscreteDomain; + using batched_interpolation_domain_type = ddc::DiscreteDomain; using batch_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, bsplines_type, Tag>; - using spline_domain_type = + using batched_batched_spline_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq, ddc::detail::TypeSeq>>; - using spline_tr_domain_type = + using batched_spline_tr_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, ddc::type_seq_remove_t< ddc::detail::TypeSeq, ddc::detail::TypeSeq>>>; - using derivs_domain_type = + using batched_derivs_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq, @@ -152,7 +152,7 @@ class SplineBuilder static constexpr ddc::BoundCond s_bc_xmax = BcXmax; private: - vals_domain_type m_vals_domain; + batched_interpolation_domain_type m_batched_interpolation_domain; int m_offset; @@ -165,10 +165,10 @@ class SplineBuilder int compute_offset(interpolation_domain_type const& interpolation_domain); explicit SplineBuilder( - vals_domain_type const& vals_domain, + batched_interpolation_domain_type const& batched_interpolation_domain, std::optional cols_per_chunk = std::nullopt, std::optional preconditionner_max_block_size = std::nullopt) - : m_vals_domain(vals_domain) + : m_batched_interpolation_domain(batched_interpolation_domain) , m_offset(compute_offset(interpolation_domain())) , m_dx((ddc::discrete_space().rmax() - ddc::discrete_space().rmin()) / ddc::discrete_space().ncells()) @@ -212,9 +212,9 @@ class SplineBuilder */ SplineBuilder& operator=(SplineBuilder&& x) = default; - vals_domain_type vals_domain() const noexcept + batched_interpolation_domain_type batched_interpolation_domain() const noexcept { - return m_vals_domain; + return m_batched_interpolation_domain; } /** @@ -227,15 +227,15 @@ class SplineBuilder */ interpolation_domain_type interpolation_domain() const noexcept { - return interpolation_domain_type(vals_domain()); + return interpolation_domain_type(batched_interpolation_domain()); } batch_domain_type batch_domain() const noexcept { - return ddc::remove_dims_of(vals_domain(), interpolation_domain()); + return ddc::remove_dims_of(batched_interpolation_domain(), interpolation_domain()); } - ddc::DiscreteDomain bsplines_domain() const noexcept // TODO : clarify name + ddc::DiscreteDomain spline_domain() const noexcept // TODO : clarify name { return ddc::discrete_space().full_domain(); } @@ -248,31 +248,31 @@ class SplineBuilder * * @return The domain for the splines. */ - spline_domain_type spline_domain() const noexcept + batched_batched_spline_domain_type batched_spline_domain() const noexcept { return ddc::replace_dim_of< interpolation_mesh_type, - bsplines_type>(vals_domain(), bsplines_domain()); + bsplines_type>(batched_interpolation_domain(), spline_domain()); } - spline_tr_domain_type spline_tr_domain() const noexcept + batched_spline_tr_domain_type spline_tr_domain() const noexcept { - return spline_tr_domain_type(bsplines_domain(), batch_domain()); + return batched_spline_tr_domain_type(spline_domain(), batch_domain()); } - derivs_domain_type derivs_xmin_domain() const noexcept + batched_derivs_domain_type derivs_xmin_domain() const noexcept { return ddc::replace_dim_of( - vals_domain(), + batched_interpolation_domain(), ddc::DiscreteDomain( ddc::DiscreteElement(1), ddc::DiscreteVector(s_nbc_xmin))); } - derivs_domain_type derivs_xmax_domain() const noexcept + batched_derivs_domain_type derivs_xmax_domain() const noexcept { return ddc::replace_dim_of( - vals_domain(), + batched_interpolation_domain(), ddc::DiscreteDomain( ddc::DiscreteElement(1), ddc::DiscreteVector(s_nbc_xmax))); @@ -309,15 +309,20 @@ class SplineBuilder */ template void operator()( - ddc::ChunkSpan spline, - ddc::ChunkSpan vals, - std::optional< - ddc::ChunkSpan> const - derivs_xmin + ddc::ChunkSpan spline, + ddc::ChunkSpan + vals, + std::optional> const derivs_xmin = std::nullopt, - std::optional< - ddc::ChunkSpan> const - derivs_xmax + std::optional> const derivs_xmax = std::nullopt) const; private: @@ -629,12 +634,18 @@ void SplineBuilder< Solver, IDimX...>:: operator()( - ddc::ChunkSpan spline, - ddc::ChunkSpan vals, - std::optional> const - derivs_xmin, - std::optional> const - derivs_xmax) const + ddc::ChunkSpan spline, + ddc::ChunkSpan vals, + std::optional> const derivs_xmin, + std::optional> const derivs_xmax) const { assert(vals.template extent() == ddc::discrete_space().nbasis() - s_nbe_xmin - s_nbe_xmax); diff --git a/include/ddc/kernels/splines/spline_builder_2d.hpp b/include/ddc/kernels/splines/spline_builder_2d.hpp index 5d815527e..d4c9691e1 100644 --- a/include/ddc/kernels/splines/spline_builder_2d.hpp +++ b/include/ddc/kernels/splines/spline_builder_2d.hpp @@ -113,26 +113,26 @@ class SplineBuilder2D using interpolation_domain_type = ddc::DiscreteDomain; - using vals_domain_type = ddc::DiscreteDomain; + using batched_interpolation_domain_type = ddc::DiscreteDomain; using batch_domain_type = ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq>>; - using spline_domain_type + using batched_batched_spline_domain_type = ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq, ddc::detail::TypeSeq>>; - using derivs_domain_type1 = typename builder_type1::derivs_domain_type; - using derivs_domain_type2 + using batched_derivs_domain_type1 = typename builder_type1::batched_derivs_domain_type; + using batched_derivs_domain_type2 = ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq, ddc::detail::TypeSeq>>; - using derivs_domain_type + using batched_derivs_domain_type = ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq, @@ -147,24 +147,27 @@ class SplineBuilder2D /** * @brief Create a new SplineBuilder2D. * - * @param vals_domain + * @param batched_interpolation_domain * The 2D domain on which points will be provided in order to * create the 2D spline approximation. * @param cols_per_chunk The number of columns in the rhs passed to the underlying linear solver. * @param preconditionner_max_block_size The block size of in the block Jacobi preconditioner. */ explicit SplineBuilder2D( - vals_domain_type const& vals_domain, + batched_interpolation_domain_type const& batched_interpolation_domain, std::optional cols_per_chunk = std::nullopt, std::optional preconditionner_max_block_size = std::nullopt) - : m_spline_builder1(vals_domain, cols_per_chunk, preconditionner_max_block_size) + : m_spline_builder1( + batched_interpolation_domain, + cols_per_chunk, + preconditionner_max_block_size) , m_spline_builder_deriv1(ddc::replace_dim_of( - m_spline_builder1.vals_domain(), + m_spline_builder1.batched_interpolation_domain(), ddc::DiscreteDomain( ddc::DiscreteElement(1), ddc::DiscreteVector(bsplines_type2::degree() / 2)))) , m_spline_builder2( - m_spline_builder1.spline_domain(), + m_spline_builder1.batched_spline_domain(), cols_per_chunk, preconditionner_max_block_size) { @@ -200,9 +203,9 @@ class SplineBuilder2D */ SplineBuilder2D& operator=(SplineBuilder2D&& x) = default; - vals_domain_type vals_domain() const noexcept + batched_interpolation_domain_type batched_interpolation_domain() const noexcept { - return m_spline_builder1.vals_domain(); + return m_spline_builder1.batched_interpolation_domain(); } /** @@ -222,7 +225,7 @@ class SplineBuilder2D batch_domain_type batch_domain() const noexcept { - return ddc::remove_dims_of(vals_domain(), interpolation_domain()); + return ddc::remove_dims_of(batched_interpolation_domain(), interpolation_domain()); } /** @@ -233,7 +236,7 @@ class SplineBuilder2D * * @return The 2D domain for the splines. */ - ddc::DiscreteDomain bsplines_domain() + ddc::DiscreteDomain spline_domain() const noexcept // TODO : clarify name { return ddc::DiscreteDomain( @@ -241,13 +244,13 @@ class SplineBuilder2D ddc::discrete_space().full_domain()); } - spline_domain_type spline_domain() const noexcept + batched_batched_spline_domain_type batched_spline_domain() const noexcept { return ddc::replace_dim_of( ddc::replace_dim_of< interpolation_mesh_type2, - bsplines_type2>(vals_domain(), bsplines_domain()), - bsplines_domain()); + bsplines_type2>(batched_interpolation_domain(), spline_domain()), + spline_domain()); } /** @@ -288,39 +291,56 @@ class SplineBuilder2D */ template void operator()( - ddc::ChunkSpan spline, - ddc::ChunkSpan vals, - std::optional< - ddc::ChunkSpan> const - derivs_min1 + ddc::ChunkSpan spline, + ddc::ChunkSpan + vals, + std::optional> const derivs_min1 = std::nullopt, - std::optional< - ddc::ChunkSpan> const - derivs_max1 + std::optional> const derivs_max1 = std::nullopt, - std::optional< - ddc::ChunkSpan> const - derivs_min2 + std::optional> const derivs_min2 = std::nullopt, - std::optional< - ddc::ChunkSpan> const - derivs_max2 + std::optional> const derivs_max2 = std::nullopt, - std::optional< - ddc::ChunkSpan> const - mixed_derivs_min1_min2 + std::optional> const mixed_derivs_min1_min2 = std::nullopt, - std::optional< - ddc::ChunkSpan> const - mixed_derivs_max1_min2 + std::optional> const mixed_derivs_max1_min2 = std::nullopt, - std::optional< - ddc::ChunkSpan> const - mixed_derivs_min1_max2 + std::optional> const mixed_derivs_min1_max2 = std::nullopt, - std::optional< - ddc::ChunkSpan> const - mixed_derivs_max1_max2 + std::optional> const mixed_derivs_max1_max2 = std::nullopt) const; }; @@ -353,29 +373,53 @@ void SplineBuilder2D< Solver, IDimX...>:: operator()( - ddc::ChunkSpan spline, - ddc::ChunkSpan vals, - std::optional> const - derivs_min1, - std::optional> const - derivs_max1, - std::optional> const - derivs_min2, - std::optional> const - derivs_max2, - std::optional> const - mixed_derivs_min1_min2, - std::optional> const - mixed_derivs_max1_min2, - std::optional> const - mixed_derivs_min1_max2, - std::optional> const - mixed_derivs_max1_max2) const + ddc::ChunkSpan spline, + ddc::ChunkSpan vals, + std::optional> const derivs_min1, + std::optional> const derivs_max1, + std::optional> const derivs_min2, + std::optional> const derivs_max2, + std::optional> const mixed_derivs_min1_min2, + std::optional> const mixed_derivs_max1_min2, + std::optional> const mixed_derivs_min1_max2, + std::optional> const mixed_derivs_max1_max2) const { // TODO: perform computations along dimension 1 on different streams ? // Spline1-transform derivs_min2 (to spline1_deriv_min) ddc::Chunk spline1_deriv_min_alloc( - m_spline_builder_deriv1.spline_domain(), + m_spline_builder_deriv1.batched_spline_domain(), ddc::KokkosAllocator()); auto spline1_deriv_min = spline1_deriv_min_alloc.span_view(); auto spline1_deriv_min_opt = std::optional(spline1_deriv_min.span_cview()); @@ -391,7 +435,7 @@ operator()( // Spline1-transform vals (to spline1) ddc::Chunk spline1_alloc( - m_spline_builder1.spline_domain(), + m_spline_builder1.batched_spline_domain(), ddc::KokkosAllocator()); ddc::ChunkSpan spline1 = spline1_alloc.span_view(); @@ -399,7 +443,7 @@ operator()( // Spline1-transform derivs_max2 (to spline1_deriv_max) ddc::Chunk spline1_deriv_max_alloc( - m_spline_builder_deriv1.spline_domain(), + m_spline_builder_deriv1.batched_spline_domain(), ddc::KokkosAllocator()); auto spline1_deriv_max = spline1_deriv_max_alloc.span_view(); auto spline1_deriv_max_opt = std::optional(spline1_deriv_max.span_cview()); diff --git a/include/ddc/kernels/splines/spline_evaluator.hpp b/include/ddc/kernels/splines/spline_evaluator.hpp index fc5295c2d..dff77f8e7 100644 --- a/include/ddc/kernels/splines/spline_evaluator.hpp +++ b/include/ddc/kernels/splines/spline_evaluator.hpp @@ -49,9 +49,9 @@ class SplineEvaluator using interpolation_domain_type = ddc::DiscreteDomain; - using vals_domain_type = ddc::DiscreteDomain; + using batched_interpolation_domain_type = ddc::DiscreteDomain; - using bsplines_domain_type = ddc::DiscreteDomain; + using batched_spline_domain_type = ddc::DiscreteDomain; using batch_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, bsplines_type, Tag>; - using spline_domain_type = + using batched_batched_spline_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq, @@ -91,7 +91,7 @@ class SplineEvaluator ddc::Coordinate, ddc::ChunkSpan< double const, - bsplines_domain_type, + batched_spline_domain_type, std::experimental::layout_right, memory_space>>, "LeftExtrapolationRule::operator() has to be callable with usual arguments."); @@ -102,7 +102,7 @@ class SplineEvaluator ddc::Coordinate, ddc::ChunkSpan< double const, - bsplines_domain_type, + batched_spline_domain_type, std::experimental::layout_right, memory_space>>, "RightExtrapolationRule::operator() has to be callable with usual arguments."); @@ -138,7 +138,7 @@ class SplineEvaluator template KOKKOS_FUNCTION double operator()( ddc::Coordinate const& coord_eval, - ddc::ChunkSpan const + ddc::ChunkSpan const spline_coef) const { return eval(coord_eval, spline_coef); @@ -146,14 +146,18 @@ class SplineEvaluator template void operator()( - ddc::ChunkSpan const spline_eval, + ddc::ChunkSpan const + spline_eval, ddc::ChunkSpan< ddc::Coordinate const, - vals_domain_type, + batched_interpolation_domain_type, Layout2, memory_space> const coords_eval, - ddc::ChunkSpan const - spline_coef) const + ddc::ChunkSpan< + double const, + batched_batched_spline_domain_type, + Layout3, + memory_space> const spline_coef) const { interpolation_domain_type const interpolation_domain(spline_eval.domain()); batch_domain_type const batch_domain(spline_eval.domain()); @@ -174,7 +178,7 @@ class SplineEvaluator template KOKKOS_FUNCTION double deriv( ddc::Coordinate const& coord_eval, - ddc::ChunkSpan const + ddc::ChunkSpan const spline_coef) const { return eval_no_bc(coord_eval, spline_coef); @@ -182,14 +186,18 @@ class SplineEvaluator template void deriv( - ddc::ChunkSpan const spline_eval, + ddc::ChunkSpan const + spline_eval, ddc::ChunkSpan< ddc::Coordinate const, - vals_domain_type, + batched_interpolation_domain_type, Layout2, memory_space> const coords_eval, - ddc::ChunkSpan const - spline_coef) const + ddc::ChunkSpan< + double const, + batched_batched_spline_domain_type, + Layout3, + memory_space> const spline_coef) const { interpolation_domain_type const interpolation_domain(spline_eval.domain()); batch_domain_type const batch_domain(spline_eval.domain()); @@ -211,8 +219,11 @@ class SplineEvaluator template void integrate( ddc::ChunkSpan const integrals, - ddc::ChunkSpan const - spline_coef) const + ddc::ChunkSpan< + double const, + batched_batched_spline_domain_type, + Layout2, + memory_space> const spline_coef) const { batch_domain_type const batch_domain(integrals.domain()); ddc::Chunk values_alloc( @@ -228,7 +239,7 @@ class SplineEvaluator batch_domain, KOKKOS_LAMBDA(typename batch_domain_type::discrete_element_type const j) { integrals(j) = 0; - for (typename bsplines_domain_type::discrete_element_type const i : + for (typename batched_spline_domain_type::discrete_element_type const i : values.domain()) { integrals(j) += spline_coef(i, j) * values(i); } @@ -239,7 +250,7 @@ class SplineEvaluator template KOKKOS_INLINE_FUNCTION double eval( ddc::Coordinate const& coord_eval, - ddc::ChunkSpan const + ddc::ChunkSpan const spline_coef) const { ddc::Coordinate @@ -269,7 +280,7 @@ class SplineEvaluator template KOKKOS_INLINE_FUNCTION double eval_no_bc( ddc::Coordinate const& coord_eval, - ddc::ChunkSpan const + ddc::ChunkSpan const spline_coef) const { static_assert( diff --git a/include/ddc/kernels/splines/spline_evaluator_2d.hpp b/include/ddc/kernels/splines/spline_evaluator_2d.hpp index 168ab7b08..30a3c3732 100644 --- a/include/ddc/kernels/splines/spline_evaluator_2d.hpp +++ b/include/ddc/kernels/splines/spline_evaluator_2d.hpp @@ -66,11 +66,11 @@ class SplineEvaluator2D using interpolation_domain_type = ddc::DiscreteDomain; - using vals_domain_type = ddc::DiscreteDomain; + using batched_interpolation_domain_type = ddc::DiscreteDomain; - using bsplines_domain_type1 = ddc::DiscreteDomain; - using bsplines_domain_type2 = ddc::DiscreteDomain; - using bsplines_domain_type = ddc::DiscreteDomain; + using batched_spline_domain_type1 = ddc::DiscreteDomain; + using batched_spline_domain_type2 = ddc::DiscreteDomain; + using batched_spline_domain_type = ddc::DiscreteDomain; using batch_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, bsplines_type2, Tag>>; - using spline_domain_type = + using batched_batched_spline_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq, @@ -124,7 +124,7 @@ class SplineEvaluator2D ddc::Coordinate, ddc::ChunkSpan< double const, - bsplines_domain_type, + batched_spline_domain_type, std::experimental::layout_right, memory_space>>, "LeftExtrapolationRule1::operator() has to be callable " @@ -136,7 +136,7 @@ class SplineEvaluator2D ddc::Coordinate, ddc::ChunkSpan< double const, - bsplines_domain_type, + batched_spline_domain_type, std::experimental::layout_right, memory_space>>, "RightExtrapolationRule1::operator() has to be callable " @@ -148,7 +148,7 @@ class SplineEvaluator2D ddc::Coordinate, ddc::ChunkSpan< double const, - bsplines_domain_type, + batched_spline_domain_type, std::experimental::layout_right, memory_space>>, "LeftExtrapolationRule2::operator() has to be callable " @@ -160,7 +160,7 @@ class SplineEvaluator2D ddc::Coordinate, ddc::ChunkSpan< double const, - bsplines_domain_type, + batched_spline_domain_type, std::experimental::layout_right, memory_space>>, "RightExtrapolationRule2::operator() has to be callable " @@ -271,7 +271,7 @@ class SplineEvaluator2D template KOKKOS_FUNCTION double operator()( ddc::Coordinate const& coord_eval, - ddc::ChunkSpan const + ddc::ChunkSpan const spline_coef) const { return eval(coord_eval, spline_coef); @@ -279,14 +279,18 @@ class SplineEvaluator2D template void operator()( - ddc::ChunkSpan const spline_eval, + ddc::ChunkSpan const + spline_eval, ddc::ChunkSpan< ddc::Coordinate const, - vals_domain_type, + batched_interpolation_domain_type, Layout2, memory_space> const coords_eval, - ddc::ChunkSpan const - spline_coef) const + ddc::ChunkSpan< + double const, + batched_batched_spline_domain_type, + Layout3, + memory_space> const spline_coef) const { batch_domain_type batch_domain(coords_eval.domain()); interpolation_domain_type1 const interpolation_domain1(spline_eval.domain()); @@ -319,7 +323,7 @@ class SplineEvaluator2D template KOKKOS_FUNCTION double deriv_dim_1( ddc::Coordinate const& coord_eval, - ddc::ChunkSpan const + ddc::ChunkSpan const spline_coef) const { return eval_no_bc(coord_eval, spline_coef); @@ -338,7 +342,7 @@ class SplineEvaluator2D template KOKKOS_FUNCTION double deriv_dim_2( ddc::Coordinate const& coord_eval, - ddc::ChunkSpan const + ddc::ChunkSpan const spline_coef) const { return eval_no_bc(coord_eval, spline_coef); @@ -357,7 +361,7 @@ class SplineEvaluator2D template KOKKOS_FUNCTION double deriv_1_and_2( ddc::Coordinate const& coord_eval, - ddc::ChunkSpan const + ddc::ChunkSpan const spline_coef) const { return eval_no_bc(coord_eval, spline_coef); @@ -366,7 +370,7 @@ class SplineEvaluator2D template KOKKOS_FUNCTION double deriv( ddc::Coordinate const& coord_eval, - ddc::ChunkSpan const + ddc::ChunkSpan const spline_coef) const { static_assert( @@ -389,7 +393,7 @@ class SplineEvaluator2D template KOKKOS_FUNCTION double deriv2( ddc::Coordinate const& coord_eval, - ddc::ChunkSpan const + ddc::ChunkSpan const spline_coef) const { static_assert( @@ -416,14 +420,18 @@ class SplineEvaluator2D */ template void deriv_dim_1( - ddc::ChunkSpan const spline_eval, + ddc::ChunkSpan const + spline_eval, ddc::ChunkSpan< ddc::Coordinate const, - vals_domain_type, + batched_interpolation_domain_type, Layout2, memory_space> const coords_eval, - ddc::ChunkSpan const - spline_coef) const + ddc::ChunkSpan< + double const, + batched_batched_spline_domain_type, + Layout3, + memory_space> const spline_coef) const { batch_domain_type batch_domain(coords_eval.domain()); interpolation_domain_type1 const interpolation_domain1(spline_eval.domain()); @@ -457,14 +465,18 @@ class SplineEvaluator2D */ template void deriv_dim_2( - ddc::ChunkSpan const spline_eval, + ddc::ChunkSpan const + spline_eval, ddc::ChunkSpan< ddc::Coordinate const, - vals_domain_type, + batched_interpolation_domain_type, Layout2, memory_space> const coords_eval, - ddc::ChunkSpan const - spline_coef) const + ddc::ChunkSpan< + double const, + batched_batched_spline_domain_type, + Layout3, + memory_space> const spline_coef) const { batch_domain_type batch_domain(coords_eval.domain()); interpolation_domain_type1 const interpolation_domain1(spline_eval.domain()); @@ -498,14 +510,18 @@ class SplineEvaluator2D */ template void deriv_1_and_2( - ddc::ChunkSpan const spline_eval, + ddc::ChunkSpan const + spline_eval, ddc::ChunkSpan< ddc::Coordinate const, - vals_domain_type, + batched_interpolation_domain_type, Layout2, memory_space> const coords_eval, - ddc::ChunkSpan const - spline_coef) const + ddc::ChunkSpan< + double const, + batched_batched_spline_domain_type, + Layout3, + memory_space> const spline_coef) const { batch_domain_type batch_domain(coords_eval.domain()); interpolation_domain_type1 const interpolation_domain1(spline_eval.domain()); @@ -529,14 +545,18 @@ class SplineEvaluator2D template void deriv( - ddc::ChunkSpan const spline_eval, + ddc::ChunkSpan const + spline_eval, ddc::ChunkSpan< ddc::Coordinate const, - vals_domain_type, + batched_interpolation_domain_type, Layout2, memory_space> const coords_eval, - ddc::ChunkSpan const - spline_coef) const + ddc::ChunkSpan< + double const, + batched_batched_spline_domain_type, + Layout3, + memory_space> const spline_coef) const { static_assert( std::is_same_v< @@ -563,14 +583,18 @@ class SplineEvaluator2D class Layout3, class... CoordsDims> void deriv2( - ddc::ChunkSpan const spline_eval, + ddc::ChunkSpan const + spline_eval, ddc::ChunkSpan< ddc::Coordinate const, - vals_domain_type, + batched_interpolation_domain_type, Layout2, memory_space> const coords_eval, - ddc::ChunkSpan const - spline_coef) const + ddc::ChunkSpan< + double const, + batched_batched_spline_domain_type, + Layout3, + memory_space> const spline_coef) const { static_assert( (std::is_same_v< @@ -594,8 +618,11 @@ class SplineEvaluator2D template void integrate( ddc::ChunkSpan const integrals, - ddc::ChunkSpan const - spline_coef) const + ddc::ChunkSpan< + double const, + batched_batched_spline_domain_type, + Layout2, + memory_space> const spline_coef) const { batch_domain_type batch_domain(integrals.domain()); ddc::Chunk values1_alloc( @@ -618,9 +645,9 @@ class SplineEvaluator2D batch_domain, KOKKOS_LAMBDA(typename batch_domain_type::discrete_element_type const j) { integrals(j) = 0; - for (typename bsplines_domain_type1::discrete_element_type const i1 : + for (typename batched_spline_domain_type1::discrete_element_type const i1 : values1.domain()) { - for (typename bsplines_domain_type2::discrete_element_type const i2 : + for (typename batched_spline_domain_type2::discrete_element_type const i2 : values2.domain()) { integrals(j) += spline_coef(i1, i2, j) * values1(i1) * values2(i2); } @@ -651,7 +678,7 @@ class SplineEvaluator2D template KOKKOS_INLINE_FUNCTION double eval( ddc::Coordinate coord_eval, - ddc::ChunkSpan const + ddc::ChunkSpan const spline_coef) const { using Dim1 = typename interpolation_mesh_type1::continuous_dimension_type; @@ -720,7 +747,7 @@ class SplineEvaluator2D template KOKKOS_INLINE_FUNCTION double eval_no_bc( ddc::Coordinate const& coord_eval, - ddc::ChunkSpan const + ddc::ChunkSpan const spline_coef) const { static_assert( diff --git a/tests/splines/batched_2d_spline_builder.cpp b/tests/splines/batched_2d_spline_builder.cpp index 0f5de6cc8..17137e3b1 100644 --- a/tests/splines/batched_2d_spline_builder.cpp +++ b/tests/splines/batched_2d_spline_builder.cpp @@ -275,7 +275,7 @@ static void Batched2dSplineTest() // Compute usefull domains (dom_interpolation, dom_batch, dom_bsplines and dom_spline) ddc::DiscreteDomain, IDim> const dom_interpolation = spline_builder.interpolation_domain(); - auto const dom_spline = spline_builder.spline_domain(); + auto const dom_spline = spline_builder.batched_spline_domain(); // Allocate and fill a chunk containing values to be passed as input to spline_builder. Those are values of cosine along interest dimension duplicated along batch dimensions ddc::Chunk vals1_cpu_alloc( diff --git a/tests/splines/batched_spline_builder.cpp b/tests/splines/batched_spline_builder.cpp index 8eeb433b3..4070e263a 100644 --- a/tests/splines/batched_spline_builder.cpp +++ b/tests/splines/batched_spline_builder.cpp @@ -224,7 +224,7 @@ static void BatchedSplineTest() // Compute usefull domains (dom_interpolation, dom_batch, dom_bsplines and dom_spline) ddc::DiscreteDomain> const dom_interpolation = spline_builder.interpolation_domain(); auto const dom_batch = spline_builder.batch_domain(); - auto const dom_spline = spline_builder.spline_domain(); + auto const dom_spline = spline_builder.batched_spline_domain(); // Allocate and fill a chunk containing values to be passed as input to spline_builder. Those are values of cosine along interest dimension duplicated along batch dimensions ddc::Chunk vals1_cpu_alloc( diff --git a/tests/splines/extrapolation_rule.cpp b/tests/splines/extrapolation_rule.cpp index 864b51f76..fae128159 100644 --- a/tests/splines/extrapolation_rule.cpp +++ b/tests/splines/extrapolation_rule.cpp @@ -234,7 +234,7 @@ static void ExtrapolationRuleSplineTest() // Compute usefull domains (dom_interpolation, dom_batch, dom_bsplines and dom_spline) ddc::DiscreteDomain, IDim> const dom_interpolation = spline_builder.interpolation_domain(); - auto const dom_spline = spline_builder.spline_domain(); + auto const dom_spline = spline_builder.batched_spline_domain(); // Allocate and fill a chunk containing values to be passed as input to spline_builder. Those are values of cosine along interest dimension duplicated along batch dimensions ddc::Chunk vals1_cpu_alloc( diff --git a/tests/splines/periodicity_spline_builder.cpp b/tests/splines/periodicity_spline_builder.cpp index bed04565c..18c7b2b7c 100644 --- a/tests/splines/periodicity_spline_builder.cpp +++ b/tests/splines/periodicity_spline_builder.cpp @@ -139,7 +139,7 @@ static void PeriodicitySplineBuilderTest() spline_builder(dom_vals); // Compute usefull domains (dom_interpolation, dom_batch, dom_bsplines and dom_spline) - ddc::DiscreteDomain> const dom_bsplines = spline_builder.bsplines_domain(); + ddc::DiscreteDomain> const dom_bsplines = spline_builder.spline_domain(); // Allocate and fill a chunk containing values to be passed as input to spline_builder. Those are values of cosine along interest dimension duplicated along batch dimensions ddc::Chunk vals1_cpu_alloc( From 84a5ca710fc2cf863c247a66746ae4882b5d0bdd Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 3 Apr 2024 10:36:52 +0200 Subject: [PATCH 002/189] missing sed in benchmark --- benchmarks/splines.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/benchmarks/splines.cpp b/benchmarks/splines.cpp index f9f5b8cab..750c7425b 100644 --- a/benchmarks/splines.cpp +++ b/benchmarks/splines.cpp @@ -127,11 +127,11 @@ static void characteristics_advection(benchmark::State& state) DDimY> spline_evaluator(periodic_extrapolation, periodic_extrapolation); ddc::Chunk coef_alloc( - spline_builder.spline_domain(), + spline_builder.batched_spline_domain(), ddc::KokkosAllocator()); ddc::ChunkSpan coef = coef_alloc.span_view(); ddc::Chunk feet_coords_alloc( - spline_builder.vals_domain(), + spline_builder.batched_interpolation_domain(), ddc::KokkosAllocator< ddc::Coordinate, Kokkos::DefaultExecutionSpace::memory_space>()); From 96d4fdb7e7e8082b9c5ad4d7954a5394c558e864 Mon Sep 17 00:00:00 2001 From: blegouix Date: Mon, 15 Apr 2024 17:41:53 +0200 Subject: [PATCH 003/189] fix --- .../ddc/kernels/splines/spline_builder.hpp | 8 +-- .../ddc/kernels/splines/spline_builder_2d.hpp | 8 +-- .../ddc/kernels/splines/spline_evaluator.hpp | 24 ++++----- .../kernels/splines/spline_evaluator_2d.hpp | 50 +++++++++---------- 4 files changed, 45 insertions(+), 45 deletions(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index 0d841d492..72dcdda78 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -89,7 +89,7 @@ class SplineBuilder using spline_dim_type = std::conditional_t, bsplines_type, Tag>; - using batched_batched_spline_domain_type = + using batched_spline_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq, @@ -248,7 +248,7 @@ class SplineBuilder * * @return The domain for the splines. */ - batched_batched_spline_domain_type batched_spline_domain() const noexcept + batched_spline_domain_type batched_spline_domain() const noexcept { return ddc::replace_dim_of< interpolation_mesh_type, @@ -309,7 +309,7 @@ class SplineBuilder */ template void operator()( - ddc::ChunkSpan spline, + ddc::ChunkSpan spline, ddc::ChunkSpan vals, std::optional:: operator()( - ddc::ChunkSpan spline, + ddc::ChunkSpan spline, ddc::ChunkSpan vals, std::optional, ddc::detail::TypeSeq>>; - using batched_batched_spline_domain_type + using batched_spline_domain_type = ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq, @@ -244,7 +244,7 @@ class SplineBuilder2D ddc::discrete_space().full_domain()); } - batched_batched_spline_domain_type batched_spline_domain() const noexcept + batched_spline_domain_type batched_spline_domain() const noexcept { return ddc::replace_dim_of( ddc::replace_dim_of< @@ -291,7 +291,7 @@ class SplineBuilder2D */ template void operator()( - ddc::ChunkSpan spline, + ddc::ChunkSpan spline, ddc::ChunkSpan vals, std::optional:: operator()( - ddc::ChunkSpan spline, + ddc::ChunkSpan spline, ddc::ChunkSpan vals, std::optional; - using batched_spline_domain_type = ddc::DiscreteDomain; + using spline_domain_type = ddc::DiscreteDomain; using batch_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, bsplines_type, Tag>; - using batched_batched_spline_domain_type = + using batched_spline_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq, @@ -91,7 +91,7 @@ class SplineEvaluator ddc::Coordinate, ddc::ChunkSpan< double const, - batched_spline_domain_type, + spline_domain_type, std::experimental::layout_right, memory_space>>, "LeftExtrapolationRule::operator() has to be callable with usual arguments."); @@ -102,7 +102,7 @@ class SplineEvaluator ddc::Coordinate, ddc::ChunkSpan< double const, - batched_spline_domain_type, + spline_domain_type, std::experimental::layout_right, memory_space>>, "RightExtrapolationRule::operator() has to be callable with usual arguments."); @@ -138,7 +138,7 @@ class SplineEvaluator template KOKKOS_FUNCTION double operator()( ddc::Coordinate const& coord_eval, - ddc::ChunkSpan const + ddc::ChunkSpan const spline_coef) const { return eval(coord_eval, spline_coef); @@ -155,7 +155,7 @@ class SplineEvaluator memory_space> const coords_eval, ddc::ChunkSpan< double const, - batched_batched_spline_domain_type, + batched_spline_domain_type, Layout3, memory_space> const spline_coef) const { @@ -178,7 +178,7 @@ class SplineEvaluator template KOKKOS_FUNCTION double deriv( ddc::Coordinate const& coord_eval, - ddc::ChunkSpan const + ddc::ChunkSpan const spline_coef) const { return eval_no_bc(coord_eval, spline_coef); @@ -195,7 +195,7 @@ class SplineEvaluator memory_space> const coords_eval, ddc::ChunkSpan< double const, - batched_batched_spline_domain_type, + batched_spline_domain_type, Layout3, memory_space> const spline_coef) const { @@ -221,7 +221,7 @@ class SplineEvaluator ddc::ChunkSpan const integrals, ddc::ChunkSpan< double const, - batched_batched_spline_domain_type, + batched_spline_domain_type, Layout2, memory_space> const spline_coef) const { @@ -239,7 +239,7 @@ class SplineEvaluator batch_domain, KOKKOS_LAMBDA(typename batch_domain_type::discrete_element_type const j) { integrals(j) = 0; - for (typename batched_spline_domain_type::discrete_element_type const i : + for (typename spline_domain_type::discrete_element_type const i : values.domain()) { integrals(j) += spline_coef(i, j) * values(i); } @@ -250,7 +250,7 @@ class SplineEvaluator template KOKKOS_INLINE_FUNCTION double eval( ddc::Coordinate const& coord_eval, - ddc::ChunkSpan const + ddc::ChunkSpan const spline_coef) const { ddc::Coordinate @@ -280,7 +280,7 @@ class SplineEvaluator template KOKKOS_INLINE_FUNCTION double eval_no_bc( ddc::Coordinate const& coord_eval, - ddc::ChunkSpan const + ddc::ChunkSpan const spline_coef) const { static_assert( diff --git a/include/ddc/kernels/splines/spline_evaluator_2d.hpp b/include/ddc/kernels/splines/spline_evaluator_2d.hpp index 30a3c3732..69457e190 100644 --- a/include/ddc/kernels/splines/spline_evaluator_2d.hpp +++ b/include/ddc/kernels/splines/spline_evaluator_2d.hpp @@ -68,9 +68,9 @@ class SplineEvaluator2D using batched_interpolation_domain_type = ddc::DiscreteDomain; - using batched_spline_domain_type1 = ddc::DiscreteDomain; - using batched_spline_domain_type2 = ddc::DiscreteDomain; - using batched_spline_domain_type = ddc::DiscreteDomain; + using spline_domain_type1 = ddc::DiscreteDomain; + using spline_domain_type2 = ddc::DiscreteDomain; + using spline_domain_type = ddc::DiscreteDomain; using batch_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, bsplines_type2, Tag>>; - using batched_batched_spline_domain_type = + using batched_spline_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq, @@ -124,7 +124,7 @@ class SplineEvaluator2D ddc::Coordinate, ddc::ChunkSpan< double const, - batched_spline_domain_type, + spline_domain_type, std::experimental::layout_right, memory_space>>, "LeftExtrapolationRule1::operator() has to be callable " @@ -136,7 +136,7 @@ class SplineEvaluator2D ddc::Coordinate, ddc::ChunkSpan< double const, - batched_spline_domain_type, + spline_domain_type, std::experimental::layout_right, memory_space>>, "RightExtrapolationRule1::operator() has to be callable " @@ -148,7 +148,7 @@ class SplineEvaluator2D ddc::Coordinate, ddc::ChunkSpan< double const, - batched_spline_domain_type, + spline_domain_type, std::experimental::layout_right, memory_space>>, "LeftExtrapolationRule2::operator() has to be callable " @@ -160,7 +160,7 @@ class SplineEvaluator2D ddc::Coordinate, ddc::ChunkSpan< double const, - batched_spline_domain_type, + spline_domain_type, std::experimental::layout_right, memory_space>>, "RightExtrapolationRule2::operator() has to be callable " @@ -271,7 +271,7 @@ class SplineEvaluator2D template KOKKOS_FUNCTION double operator()( ddc::Coordinate const& coord_eval, - ddc::ChunkSpan const + ddc::ChunkSpan const spline_coef) const { return eval(coord_eval, spline_coef); @@ -288,7 +288,7 @@ class SplineEvaluator2D memory_space> const coords_eval, ddc::ChunkSpan< double const, - batched_batched_spline_domain_type, + batched_spline_domain_type, Layout3, memory_space> const spline_coef) const { @@ -323,7 +323,7 @@ class SplineEvaluator2D template KOKKOS_FUNCTION double deriv_dim_1( ddc::Coordinate const& coord_eval, - ddc::ChunkSpan const + ddc::ChunkSpan const spline_coef) const { return eval_no_bc(coord_eval, spline_coef); @@ -342,7 +342,7 @@ class SplineEvaluator2D template KOKKOS_FUNCTION double deriv_dim_2( ddc::Coordinate const& coord_eval, - ddc::ChunkSpan const + ddc::ChunkSpan const spline_coef) const { return eval_no_bc(coord_eval, spline_coef); @@ -361,7 +361,7 @@ class SplineEvaluator2D template KOKKOS_FUNCTION double deriv_1_and_2( ddc::Coordinate const& coord_eval, - ddc::ChunkSpan const + ddc::ChunkSpan const spline_coef) const { return eval_no_bc(coord_eval, spline_coef); @@ -370,7 +370,7 @@ class SplineEvaluator2D template KOKKOS_FUNCTION double deriv( ddc::Coordinate const& coord_eval, - ddc::ChunkSpan const + ddc::ChunkSpan const spline_coef) const { static_assert( @@ -393,7 +393,7 @@ class SplineEvaluator2D template KOKKOS_FUNCTION double deriv2( ddc::Coordinate const& coord_eval, - ddc::ChunkSpan const + ddc::ChunkSpan const spline_coef) const { static_assert( @@ -429,7 +429,7 @@ class SplineEvaluator2D memory_space> const coords_eval, ddc::ChunkSpan< double const, - batched_batched_spline_domain_type, + batched_spline_domain_type, Layout3, memory_space> const spline_coef) const { @@ -474,7 +474,7 @@ class SplineEvaluator2D memory_space> const coords_eval, ddc::ChunkSpan< double const, - batched_batched_spline_domain_type, + batched_spline_domain_type, Layout3, memory_space> const spline_coef) const { @@ -519,7 +519,7 @@ class SplineEvaluator2D memory_space> const coords_eval, ddc::ChunkSpan< double const, - batched_batched_spline_domain_type, + batched_spline_domain_type, Layout3, memory_space> const spline_coef) const { @@ -554,7 +554,7 @@ class SplineEvaluator2D memory_space> const coords_eval, ddc::ChunkSpan< double const, - batched_batched_spline_domain_type, + batched_spline_domain_type, Layout3, memory_space> const spline_coef) const { @@ -592,7 +592,7 @@ class SplineEvaluator2D memory_space> const coords_eval, ddc::ChunkSpan< double const, - batched_batched_spline_domain_type, + batched_spline_domain_type, Layout3, memory_space> const spline_coef) const { @@ -620,7 +620,7 @@ class SplineEvaluator2D ddc::ChunkSpan const integrals, ddc::ChunkSpan< double const, - batched_batched_spline_domain_type, + batched_spline_domain_type, Layout2, memory_space> const spline_coef) const { @@ -645,9 +645,9 @@ class SplineEvaluator2D batch_domain, KOKKOS_LAMBDA(typename batch_domain_type::discrete_element_type const j) { integrals(j) = 0; - for (typename batched_spline_domain_type1::discrete_element_type const i1 : + for (typename spline_domain_type1::discrete_element_type const i1 : values1.domain()) { - for (typename batched_spline_domain_type2::discrete_element_type const i2 : + for (typename spline_domain_type2::discrete_element_type const i2 : values2.domain()) { integrals(j) += spline_coef(i1, i2, j) * values1(i1) * values2(i2); } @@ -678,7 +678,7 @@ class SplineEvaluator2D template KOKKOS_INLINE_FUNCTION double eval( ddc::Coordinate coord_eval, - ddc::ChunkSpan const + ddc::ChunkSpan const spline_coef) const { using Dim1 = typename interpolation_mesh_type1::continuous_dimension_type; @@ -747,7 +747,7 @@ class SplineEvaluator2D template KOKKOS_INLINE_FUNCTION double eval_no_bc( ddc::Coordinate const& coord_eval, - ddc::ChunkSpan const + ddc::ChunkSpan const spline_coef) const { static_assert( From 077807aa9b00ecf1f57c8fcdb38a1c713acab599 Mon Sep 17 00:00:00 2001 From: Baptiste Legouix Date: Mon, 15 Apr 2024 17:44:09 +0200 Subject: [PATCH 004/189] Update include/ddc/kernels/splines/spline_builder.hpp --- include/ddc/kernels/splines/spline_builder.hpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index 72dcdda78..d5cdc6593 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -235,7 +235,7 @@ class SplineBuilder return ddc::remove_dims_of(batched_interpolation_domain(), interpolation_domain()); } - ddc::DiscreteDomain spline_domain() const noexcept // TODO : clarify name + ddc::DiscreteDomain spline_domain() const noexcept { return ddc::discrete_space().full_domain(); } From 653bab4d9e7e81a8f2e05eef18d7b10e8c78a6e9 Mon Sep 17 00:00:00 2001 From: blegouix Date: Mon, 15 Apr 2024 17:49:47 +0200 Subject: [PATCH 005/189] clang-format --- .../ddc/kernels/splines/spline_evaluator.hpp | 21 +++----- .../kernels/splines/spline_evaluator_2d.hpp | 49 ++++++------------- vendor/kokkos | 2 +- 3 files changed, 21 insertions(+), 51 deletions(-) diff --git a/include/ddc/kernels/splines/spline_evaluator.hpp b/include/ddc/kernels/splines/spline_evaluator.hpp index 8c56accee..70c578583 100644 --- a/include/ddc/kernels/splines/spline_evaluator.hpp +++ b/include/ddc/kernels/splines/spline_evaluator.hpp @@ -153,11 +153,8 @@ class SplineEvaluator batched_interpolation_domain_type, Layout2, memory_space> const coords_eval, - ddc::ChunkSpan< - double const, - batched_spline_domain_type, - Layout3, - memory_space> const spline_coef) const + ddc::ChunkSpan const + spline_coef) const { interpolation_domain_type const interpolation_domain(spline_eval.domain()); batch_domain_type const batch_domain(spline_eval.domain()); @@ -193,11 +190,8 @@ class SplineEvaluator batched_interpolation_domain_type, Layout2, memory_space> const coords_eval, - ddc::ChunkSpan< - double const, - batched_spline_domain_type, - Layout3, - memory_space> const spline_coef) const + ddc::ChunkSpan const + spline_coef) const { interpolation_domain_type const interpolation_domain(spline_eval.domain()); batch_domain_type const batch_domain(spline_eval.domain()); @@ -219,11 +213,8 @@ class SplineEvaluator template void integrate( ddc::ChunkSpan const integrals, - ddc::ChunkSpan< - double const, - batched_spline_domain_type, - Layout2, - memory_space> const spline_coef) const + ddc::ChunkSpan const + spline_coef) const { batch_domain_type const batch_domain(integrals.domain()); ddc::Chunk values_alloc( diff --git a/include/ddc/kernels/splines/spline_evaluator_2d.hpp b/include/ddc/kernels/splines/spline_evaluator_2d.hpp index 69457e190..a8aac5c35 100644 --- a/include/ddc/kernels/splines/spline_evaluator_2d.hpp +++ b/include/ddc/kernels/splines/spline_evaluator_2d.hpp @@ -286,11 +286,8 @@ class SplineEvaluator2D batched_interpolation_domain_type, Layout2, memory_space> const coords_eval, - ddc::ChunkSpan< - double const, - batched_spline_domain_type, - Layout3, - memory_space> const spline_coef) const + ddc::ChunkSpan const + spline_coef) const { batch_domain_type batch_domain(coords_eval.domain()); interpolation_domain_type1 const interpolation_domain1(spline_eval.domain()); @@ -427,11 +424,8 @@ class SplineEvaluator2D batched_interpolation_domain_type, Layout2, memory_space> const coords_eval, - ddc::ChunkSpan< - double const, - batched_spline_domain_type, - Layout3, - memory_space> const spline_coef) const + ddc::ChunkSpan const + spline_coef) const { batch_domain_type batch_domain(coords_eval.domain()); interpolation_domain_type1 const interpolation_domain1(spline_eval.domain()); @@ -472,11 +466,8 @@ class SplineEvaluator2D batched_interpolation_domain_type, Layout2, memory_space> const coords_eval, - ddc::ChunkSpan< - double const, - batched_spline_domain_type, - Layout3, - memory_space> const spline_coef) const + ddc::ChunkSpan const + spline_coef) const { batch_domain_type batch_domain(coords_eval.domain()); interpolation_domain_type1 const interpolation_domain1(spline_eval.domain()); @@ -517,11 +508,8 @@ class SplineEvaluator2D batched_interpolation_domain_type, Layout2, memory_space> const coords_eval, - ddc::ChunkSpan< - double const, - batched_spline_domain_type, - Layout3, - memory_space> const spline_coef) const + ddc::ChunkSpan const + spline_coef) const { batch_domain_type batch_domain(coords_eval.domain()); interpolation_domain_type1 const interpolation_domain1(spline_eval.domain()); @@ -552,11 +540,8 @@ class SplineEvaluator2D batched_interpolation_domain_type, Layout2, memory_space> const coords_eval, - ddc::ChunkSpan< - double const, - batched_spline_domain_type, - Layout3, - memory_space> const spline_coef) const + ddc::ChunkSpan const + spline_coef) const { static_assert( std::is_same_v< @@ -590,11 +575,8 @@ class SplineEvaluator2D batched_interpolation_domain_type, Layout2, memory_space> const coords_eval, - ddc::ChunkSpan< - double const, - batched_spline_domain_type, - Layout3, - memory_space> const spline_coef) const + ddc::ChunkSpan const + spline_coef) const { static_assert( (std::is_same_v< @@ -618,11 +600,8 @@ class SplineEvaluator2D template void integrate( ddc::ChunkSpan const integrals, - ddc::ChunkSpan< - double const, - batched_spline_domain_type, - Layout2, - memory_space> const spline_coef) const + ddc::ChunkSpan const + spline_coef) const { batch_domain_type batch_domain(integrals.domain()); ddc::Chunk values1_alloc( diff --git a/vendor/kokkos b/vendor/kokkos index 486cc745c..71a9bcae5 160000 --- a/vendor/kokkos +++ b/vendor/kokkos @@ -1 +1 @@ -Subproject commit 486cc745cb9a287f3915061455105a3ee588c616 +Subproject commit 71a9bcae52543bd065522bf3e41b5bfa467d8015 From 889b9f94f366433ac12bf73fcdaa90ea3bbb1905 Mon Sep 17 00:00:00 2001 From: blegouix Date: Tue, 16 Apr 2024 09:24:32 +0200 Subject: [PATCH 006/189] fix kokkos version change --- vendor/kokkos | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/vendor/kokkos b/vendor/kokkos index 71a9bcae5..486cc745c 160000 --- a/vendor/kokkos +++ b/vendor/kokkos @@ -1 +1 @@ -Subproject commit 71a9bcae52543bd065522bf3e41b5bfa467d8015 +Subproject commit 486cc745cb9a287f3915061455105a3ee588c616 From 6238ca3aa423359aedc9353617053dee7b1916c0 Mon Sep 17 00:00:00 2001 From: blegouix Date: Tue, 16 Apr 2024 15:40:24 +0200 Subject: [PATCH 007/189] wip --- .../ddc/kernels/splines/bsplines_uniform.hpp | 6 +++ .../splines/greville_interpolation_points.hpp | 2 +- .../splines/null_extrapolation_rule.hpp | 3 ++ .../ddc/kernels/splines/spline_builder.hpp | 48 +++++++++++++++++-- .../ddc/kernels/splines/spline_builder_2d.hpp | 7 +++ 5 files changed, 62 insertions(+), 4 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_uniform.hpp b/include/ddc/kernels/splines/bsplines_uniform.hpp index 2a0b7d1c7..c9b2f1863 100644 --- a/include/ddc/kernels/splines/bsplines_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_uniform.hpp @@ -24,6 +24,12 @@ struct UniformBSplinesBase { }; +/** + * The type of a uniform BSplines 1D basis. + * + * @tparam Tag The tag identifying the continuous dimension which supports the building of the BSplines. + * @tparam D The degree of the BSplines. + */ template class UniformBSplines : UniformBSplinesBase { diff --git a/include/ddc/kernels/splines/greville_interpolation_points.hpp b/include/ddc/kernels/splines/greville_interpolation_points.hpp index 71443c6b9..93afe9580 100644 --- a/include/ddc/kernels/splines/greville_interpolation_points.hpp +++ b/include/ddc/kernels/splines/greville_interpolation_points.hpp @@ -15,7 +15,7 @@ namespace ddc { /** - * A class which provides helper functions to initialise the Greville points from a B-Spline definition. + * A class which provides helper functions to initialize the Greville points from a B-Spline definition. * * @tparam BSplines The bspline class relative to which the Greville points will be calculated. * @tparam BcXmin The (left) boundary condition that will be used to build the splines. diff --git a/include/ddc/kernels/splines/null_extrapolation_rule.hpp b/include/ddc/kernels/splines/null_extrapolation_rule.hpp index a81930da6..b79fd5850 100644 --- a/include/ddc/kernels/splines/null_extrapolation_rule.hpp +++ b/include/ddc/kernels/splines/null_extrapolation_rule.hpp @@ -6,6 +6,9 @@ namespace ddc { +/** + * @brief A functor for describing a spline boundary value by a null extrapolation for 1D evaluator. + */ struct NullExtrapolationRule { template diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index d5cdc6593..e956ad99d 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -10,10 +10,26 @@ #include "deriv.hpp" namespace ddc { + +/** + * @brief An enum determining the backend solver of a SplineBuilder or SplineBuilder2d. + * + * An enum determining the backend solver of a SplineBuilder or SplineBuilder2d. Only GINKGO available at the moment, + * other solvers will be implemented in the futur. + */ enum class SplineSolver { GINKGO -}; // Only GINKGO available atm, other solvers will be implemented in the futur +}; +/** + * @brief An helper giving the uniform/non_uniform status of a spline interpolation mesh according to its attributes. + * + * An helper giving the uniform/non_uniform status of a spline interpolation mesh according to its attributes. + * @param is_uniform A boolean giving the presumed status before considering boundary conditions. + * @param BcXmin The Xmin boundary condition. + * @param BcXmax The Xmax boundary condition. + * @param int The degree of the spline. + */ constexpr bool is_spline_interpolation_mesh_uniform( bool const is_uniform, ddc::BoundCond const BcXmin, @@ -34,6 +50,14 @@ constexpr bool is_spline_interpolation_mesh_uniform( * of BSplines. The spline is constructed such that it respects the boundary conditions * BcXmin and BcXmax, and it interpolates the function at the points on the interpolation_mesh * associated with interpolation_mesh_type. + * @tparam ExecSpace The Kokkos execution space on which the spline transform is performed. + * @tparam MemorySpace The Kokkos memory space on which the data (interpolation function and splines coefficients) are stored. + * @tparam BSplines The BSplines dimension. + * @tparam InterpolationMesh The discrete dimension supporting the interpolation points. + * @tparam BcXmin The Xmin boundary condition. + * @tparam BcXmax The Xmax boundary condition. + * @tparam Solver The SplineSolver giving the backend used to perform the spline transform. + * @tparam IDimX A variadic template of all the discrete dimensions forming the full space (InterpolationMesh + batched dimensions). */ template < class ExecSpace, @@ -57,20 +81,29 @@ class SplineBuilder using tag_type = typename InterpolationMesh::continuous_dimension_type; public: + /** + * @brief The type of the Kokkos execution space used by this class. + */ using exec_space = ExecSpace; + /** + * @brief The type of the Kokkos memory space used by this class. + */ using memory_space = MemorySpace; /** - * @brief The type of the interpolation mesh used by this class. + * @brief The type of the interpolation mesh (discrete dimension of interest) used by this class. */ using interpolation_mesh_type = InterpolationMesh; /** - * @brief The type of the BSplines which are compatible with this class. + * @brief The BSplines dimension. */ using bsplines_type = BSplines; + /** + * @brief The deriv dimension at the boundaries. + */ using deriv_type = ddc::Deriv; /** @@ -78,13 +111,22 @@ class SplineBuilder */ using interpolation_domain_type = ddc::DiscreteDomain; + /** + * @brief The type of the whole domain representing interpolation points. + */ using batched_interpolation_domain_type = ddc::DiscreteDomain; + /** + * @brief The type of the batch domain (obtained by removing dimension of interest from whole space). + */ using batch_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq>>; + /** + * @brief The dimension WIP. + */ template using spline_dim_type = std::conditional_t, bsplines_type, Tag>; diff --git a/include/ddc/kernels/splines/spline_builder_2d.hpp b/include/ddc/kernels/splines/spline_builder_2d.hpp index eebaf1f98..1d0d2d767 100644 --- a/include/ddc/kernels/splines/spline_builder_2d.hpp +++ b/include/ddc/kernels/splines/spline_builder_2d.hpp @@ -87,7 +87,14 @@ class SplineBuilder2D */ using bsplines_type2 = typename builder_type2::bsplines_type; + /** + * @brief The type of the derivatives on boundaries in the first dimension which are compatible with this class. + */ using deriv_type1 = typename builder_type1::deriv_type; + + /** + * @brief The type of the derivatives on boundaries in the second dimension which are compatible with this class. + */ using deriv_type2 = typename builder_type2::deriv_type; /** From 6ab4a97a4908a03909a5a1b42a58d6608d885ab8 Mon Sep 17 00:00:00 2001 From: blegouix Date: Tue, 16 Apr 2024 16:13:50 +0200 Subject: [PATCH 008/189] improve consistency --- include/ddc/kernels/splines/spline_builder.hpp | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index 69717fb52..acb6a5a81 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -255,12 +255,12 @@ class SplineBuilder bsplines_type>(batched_interpolation_domain(), spline_domain()); } - batched_spline_tr_domain_type spline_tr_domain() const noexcept + batched_spline_tr_domain_type batched_spline_tr_domain() const noexcept { return batched_spline_tr_domain_type(spline_domain(), batch_domain()); } - batched_derivs_domain_type derivs_xmin_domain() const noexcept + batched_derivs_domain_type batched_derivs_xmin_domain() const noexcept { return ddc::replace_dim_of( batched_interpolation_domain(), @@ -269,7 +269,7 @@ class SplineBuilder ddc::DiscreteVector(s_nbc_xmin))); } - batched_derivs_domain_type derivs_xmax_domain() const noexcept + batched_derivs_domain_type batched_derivs_xmax_domain() const noexcept { return ddc::replace_dim_of( batched_interpolation_domain(), @@ -729,7 +729,9 @@ operator()( // TODO : Consider optimizing // Allocate and fill a transposed version of spline in order to get dimension of interest as last dimension (optimal for GPU, necessary for Ginkgo) - ddc::Chunk spline_tr_alloc(spline_tr_domain(), ddc::KokkosAllocator()); + ddc::Chunk spline_tr_alloc( + batched_spline_tr_domain(), + ddc::KokkosAllocator()); ddc::ChunkSpan spline_tr = spline_tr_alloc.span_view(); ddc::parallel_for_each( exec_space(), From 66ea1642953585804f2cab9eeb723a2c3ba3967f Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 17 Apr 2024 11:41:02 +0200 Subject: [PATCH 009/189] wip --- include/ddc/kernels/splines/spline_builder.hpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index e956ad99d..3b7b5c941 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -52,7 +52,7 @@ constexpr bool is_spline_interpolation_mesh_uniform( * associated with interpolation_mesh_type. * @tparam ExecSpace The Kokkos execution space on which the spline transform is performed. * @tparam MemorySpace The Kokkos memory space on which the data (interpolation function and splines coefficients) are stored. - * @tparam BSplines The BSplines dimension. + * @tparam BSplines The discrete dimension representing the BSplines. * @tparam InterpolationMesh The discrete dimension supporting the interpolation points. * @tparam BcXmin The Xmin boundary condition. * @tparam BcXmax The Xmax boundary condition. @@ -97,7 +97,7 @@ class SplineBuilder using interpolation_mesh_type = InterpolationMesh; /** - * @brief The BSplines dimension. + * @brief The discrete dimension representing the BSplines. */ using bsplines_type = BSplines; From 2fdb975d257cbc5a0c0e3bfde62463d816d17e0b Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 17 Apr 2024 12:16:54 +0200 Subject: [PATCH 010/189] wip --- .../ddc/kernels/splines/spline_builder.hpp | 23 +++++++++++++------ 1 file changed, 16 insertions(+), 7 deletions(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index 3b7b5c941..3bca54c9c 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -26,8 +26,8 @@ enum class SplineSolver { * * An helper giving the uniform/non_uniform status of a spline interpolation mesh according to its attributes. * @param is_uniform A boolean giving the presumed status before considering boundary conditions. - * @param BcXmin The Xmin boundary condition. - * @param BcXmax The Xmax boundary condition. + * @param BcXmin The lower boundary condition. + * @param BcXmax The upper boundary condition. * @param int The degree of the spline. */ constexpr bool is_spline_interpolation_mesh_uniform( @@ -54,8 +54,8 @@ constexpr bool is_spline_interpolation_mesh_uniform( * @tparam MemorySpace The Kokkos memory space on which the data (interpolation function and splines coefficients) are stored. * @tparam BSplines The discrete dimension representing the BSplines. * @tparam InterpolationMesh The discrete dimension supporting the interpolation points. - * @tparam BcXmin The Xmin boundary condition. - * @tparam BcXmax The Xmax boundary condition. + * @tparam BcXmin The lower boundary condition. + * @tparam BcXmax The upper boundary condition. * @tparam Solver The SplineSolver giving the backend used to perform the spline transform. * @tparam IDimX A variadic template of all the discrete dimensions forming the full space (InterpolationMesh + batched dimensions). */ @@ -125,18 +125,24 @@ class SplineBuilder ddc::detail::TypeSeq>>; /** - * @brief The dimension WIP. + * @brief Helper to get the dimension of batched_spline_domain_type associated to a dimension of batched_interpolation_domain_type. */ template using spline_dim_type = std::conditional_t, bsplines_type, Tag>; + /** + * @brief The type of the whole spline domain (cartesian product of 1D spline domain and batch domain) preserving the underlying memory layout (order of dimensions). + */ using batched_spline_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq, ddc::detail::TypeSeq>>; + /** + * @brief The type of the whole spline domain (cartesian product of 1D spline domain and batch domain) with 1D spline domain being contiguous . + */ using batched_spline_tr_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, @@ -144,6 +150,9 @@ class SplineBuilder ddc::detail::TypeSeq, ddc::detail::TypeSeq>>>; + /** + * @brief The type of the whole derivs domain (cartesian product of 1D deriv domain and batch domain) preserving the underlying memory layout (order of dimensions). + */ using batched_derivs_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, @@ -156,12 +165,12 @@ class SplineBuilder static constexpr bool s_odd = BSplines::degree() % 2; /** - * @brief The number of equations which define the boundary conditions at the lower bound. + * @brief The number of equations defining the boundary conditions at the lower bound. */ static constexpr int s_nbe_xmin = n_boundary_equations(BcXmin, BSplines::degree()); /** - * @brief The number of equations which define the boundary conditions at the upper bound. + * @brief The number of equations defining the boundary conditions at the upper bound. */ static constexpr int s_nbe_xmax = n_boundary_equations(BcXmax, BSplines::degree()); From 93ec4a0db9a0e7a994e97f6dbe34c41e07d991cc Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 17 Apr 2024 15:21:20 +0200 Subject: [PATCH 011/189] spline_builder --- .../ddc/kernels/splines/spline_builder.hpp | 84 +++++++++++++++---- 1 file changed, 70 insertions(+), 14 deletions(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index 3bca54c9c..dc692d327 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -107,7 +107,7 @@ class SplineBuilder using deriv_type = ddc::Deriv; /** - * @brief The type of the domain for the interpolation mesh used by this class. + * @brief The type of the domain for the 1D interpolation mesh used by this class. */ using interpolation_domain_type = ddc::DiscreteDomain; @@ -213,8 +213,17 @@ class SplineBuilder std::unique_ptr matrix; public: + /** + * @brief An helper to compute the offset. + */ int compute_offset(interpolation_domain_type const& interpolation_domain); + /** + * @brief Build a SplineBuilder acting on batched_interpolation_domain. + * + * @param batched_interpolation_domain The domain on which are defined the interpolation points. + * @param cols_per_chunk An hyperparameter used by the slicer (internal to the solver) to define the size of a chunk of right-and-sides of the linear problem to be computed in parallel. + */ explicit SplineBuilder( batched_interpolation_domain_type const& batched_interpolation_domain, std::optional cols_per_chunk = std::nullopt, @@ -261,43 +270,63 @@ class SplineBuilder * @param x The SplineBuilder being copied. * @returns A reference to this object. */ - SplineBuilder& operator=(SplineBuilder&& x) = default; + SplineBuilder& operator=(SplineBuilder&& x) = default; - batched_interpolation_domain_type batched_interpolation_domain() const noexcept + /** + * @brief Get the domain for the 1D interpolation mesh used by this class. + * + * Get the 1D interpolation domain associated to dimension of interest. + * + * @return The 1D domain for the grid points. + */ + interpolation_domain_type interpolation_domain() const noexcept { - return m_batched_interpolation_domain; + return interpolation_domain_type(m_batched_interpolation_domain); } /** - * @brief Get the domain from which the approximation is defined. + * @brief Get the whole domain representing interpolation points. * * Get the domain on which values of the function must be provided in order - * to build a spline approximation of the function. + * to build a spline transform of the function. * * @return The domain for the grid points. */ - interpolation_domain_type interpolation_domain() const noexcept + batched_interpolation_domain_type batched_interpolation_domain() const noexcept { - return interpolation_domain_type(batched_interpolation_domain()); + return m_batched_interpolation_domain; } + /** + * @brief Get the batch domain. + * + * Get the batch domain (obtained by removing dimension of interest from whole interpolation domain). + * + * @return The batch domain. + */ batch_domain_type batch_domain() const noexcept { return ddc::remove_dims_of(batched_interpolation_domain(), interpolation_domain()); } + /** + * @brief Get the 1D domain on which spline coefficients are defined. + * + * Get the 1D spline domain corresponding to dimension of interest. + * + * @return The 1D domain for the spline coefficients. + */ ddc::DiscreteDomain spline_domain() const noexcept { return ddc::discrete_space().full_domain(); } /** - * @brief Get the domain on which the approximation is defined. + * @brief Get the whole domain on which spline coefficients are defined, preserving memory layout. * - * Get the domain of the basis-splines for which the coefficients of the spline - * approximation must be calculated. + * Get the whole domain on which spline coefficients will be computed, preserving memory layout (order of dimensions). * - * @return The domain for the splines. + * @return The domain for the spline coefficients. */ batched_spline_domain_type batched_spline_domain() const noexcept { @@ -306,11 +335,25 @@ class SplineBuilder bsplines_type>(batched_interpolation_domain(), spline_domain()); } + /** + * @brief Get the whole domain on which spline coefficients are defined, with dimension of interest contiguous. + * + * Get the (transposed) whole domain on which spline coefficients will be computed, with dimension of interest contiguous. + * + * @return The (transposed) domain for the spline coefficients. + */ batched_spline_tr_domain_type spline_tr_domain() const noexcept { return batched_spline_tr_domain_type(spline_domain(), batch_domain()); } + /** + * @brief Get the whole domain on which derivatives on lower boundary are defined. + * + * Get the whole domain on which derivatives on lower boundary are defined. This is used only with HERMITE boundary conditions. + * + * @return The domain for the derivs values. + */ batched_derivs_domain_type derivs_xmin_domain() const noexcept { return ddc::replace_dim_of( @@ -320,6 +363,13 @@ class SplineBuilder ddc::DiscreteVector(s_nbc_xmin))); } + /** + * @brief Get the whole domain on which derivatives on upper boundary are defined. + * + * Get the whole domain on which derivatives on upper boundary are defined. This is used only with HERMITE boundary conditions. + * + * @return The domain for the derivs values. + */ batched_derivs_domain_type derivs_xmax_domain() const noexcept { return ddc::replace_dim_of( @@ -334,6 +384,10 @@ class SplineBuilder * * Get the interpolation matrix. This can be useful for debugging (as it allows * one to print the matrix) or for more complex quadrature schemes. + * + * Warning: the returned ddc::detail::Matrix class is not supposed to be exposed + * to user, which means its usage is not tested out of the scope of DDC splines transforms. + * Use at your own risk. * * @return A reference to the interpolation matrix. */ @@ -355,8 +409,10 @@ class SplineBuilder * * @param[out] spline The coefficients of the spline calculated by the function. * @param[in] vals The values of the function at the grid points. - * @param[in] derivs_xmin The values of the derivatives at the lower boundary. - * @param[in] derivs_xmax The values of the derivatives at the upper boundary. + * @param[in] derivs_xmin The values of the derivatives at the lower boundary + * (used only with HERMITE lower boundary condition). + * @param[in] derivs_xmax The values of the derivatives at the upper boundary + * (used only with HERMITE upper boundary condition). */ template void operator()( From 29367d7301107a93dcc5d7932f9272a39fb90222 Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 17 Apr 2024 15:47:16 +0200 Subject: [PATCH 012/189] changes from Emiliy's reviw --- include/ddc/kernels/splines/spline_builder.hpp | 10 +++++----- include/ddc/kernels/splines/spline_builder_2d.hpp | 4 ++-- 2 files changed, 7 insertions(+), 7 deletions(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index dc692d327..ef6ba4a72 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -92,7 +92,7 @@ class SplineBuilder using memory_space = MemorySpace; /** - * @brief The type of the interpolation mesh (discrete dimension of interest) used by this class. + * @brief The type of the interpolation discrete dimension (discrete dimension of interest) used by this class. */ using interpolation_mesh_type = InterpolationMesh; @@ -102,7 +102,7 @@ class SplineBuilder using bsplines_type = BSplines; /** - * @brief The deriv dimension at the boundaries. + * @brief The Deriv dimension at the boundaries. */ using deriv_type = ddc::Deriv; @@ -151,7 +151,7 @@ class SplineBuilder ddc::detail::TypeSeq>>>; /** - * @brief The type of the whole derivs domain (cartesian product of 1D deriv domain and batch domain) preserving the underlying memory layout (order of dimensions). + * @brief The type of the whole Derivs domain (cartesian product of 1D Deriv domain and batch domain) preserving the underlying memory layout (order of dimensions). */ using batched_derivs_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain Date: Wed, 17 Apr 2024 15:52:28 +0200 Subject: [PATCH 013/189] format --- include/ddc/kernels/splines/spline_builder.hpp | 12 ++++++------ include/ddc/kernels/splines/spline_builder_2d.hpp | 4 ++-- 2 files changed, 8 insertions(+), 8 deletions(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index ef6ba4a72..b9ea5a3af 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -101,7 +101,7 @@ class SplineBuilder */ using bsplines_type = BSplines; - /** + /** * @brief The Deriv dimension at the boundaries. */ using deriv_type = ddc::Deriv; @@ -124,7 +124,7 @@ class SplineBuilder ddc::detail::TypeSeq, ddc::detail::TypeSeq>>; - /** + /** * @brief Helper to get the dimension of batched_spline_domain_type associated to a dimension of batched_interpolation_domain_type. */ template @@ -140,7 +140,7 @@ class SplineBuilder ddc::detail::TypeSeq, ddc::detail::TypeSeq>>; - /** + /** * @brief The type of the whole spline domain (cartesian product of 1D spline domain and batch domain) with 1D spline domain being contiguous . */ using batched_spline_tr_domain_type = @@ -270,7 +270,7 @@ class SplineBuilder * @param x The SplineBuilder being copied. * @returns A reference to this object. */ - SplineBuilder& operator=(SplineBuilder&& x) = default; + SplineBuilder& operator=(SplineBuilder&& x) = default; /** * @brief Get the domain for the 1D interpolation mesh used by this class. @@ -309,7 +309,7 @@ class SplineBuilder return ddc::remove_dims_of(batched_interpolation_domain(), interpolation_domain()); } - /** + /** * @brief Get the 1D domain on which spline coefficients are defined. * * Get the 1D spline domain corresponding to dimension of interest. @@ -363,7 +363,7 @@ class SplineBuilder ddc::DiscreteVector(s_nbc_xmin))); } - /** + /** * @brief Get the whole domain on which derivatives on upper boundary are defined. * * Get the whole domain on which derivatives on upper boundary are defined. This is used only with HERMITE boundary conditions. diff --git a/include/ddc/kernels/splines/spline_builder_2d.hpp b/include/ddc/kernels/splines/spline_builder_2d.hpp index f2072ddc6..872bf2956 100644 --- a/include/ddc/kernels/splines/spline_builder_2d.hpp +++ b/include/ddc/kernels/splines/spline_builder_2d.hpp @@ -87,12 +87,12 @@ class SplineBuilder2D */ using bsplines_type2 = typename builder_type2::bsplines_type; - /** + /** * @brief The type of the Deriv domain on boundaries in the first dimension which are compatible with this class. */ using deriv_type1 = typename builder_type1::deriv_type; - /** + /** * @brief The type of the Deriv domain on boundaries in the second dimension which are compatible with this class. */ using deriv_type2 = typename builder_type2::deriv_type; From 84e76df62c3832ea8f4e55fb4c57b083e53406ce Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 17 Apr 2024 16:30:31 +0200 Subject: [PATCH 014/189] minor --- include/ddc/kernels/splines/greville_interpolation_points.hpp | 2 +- include/ddc/kernels/splines/spline_builder.hpp | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/include/ddc/kernels/splines/greville_interpolation_points.hpp b/include/ddc/kernels/splines/greville_interpolation_points.hpp index 93afe9580..71443c6b9 100644 --- a/include/ddc/kernels/splines/greville_interpolation_points.hpp +++ b/include/ddc/kernels/splines/greville_interpolation_points.hpp @@ -15,7 +15,7 @@ namespace ddc { /** - * A class which provides helper functions to initialize the Greville points from a B-Spline definition. + * A class which provides helper functions to initialise the Greville points from a B-Spline definition. * * @tparam BSplines The bspline class relative to which the Greville points will be calculated. * @tparam BcXmin The (left) boundary condition that will be used to build the splines. diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index b9ea5a3af..722987513 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -220,7 +220,7 @@ class SplineBuilder /** * @brief Build a SplineBuilder acting on batched_interpolation_domain. - * + * * @param batched_interpolation_domain The domain on which are defined the interpolation points. * @param cols_per_chunk An hyperparameter used by the slicer (internal to the solver) to define the size of a chunk of right-and-sides of the linear problem to be computed in parallel. */ From aa7b594ccc4219c1845b2b6b52b6e6118d5a15a3 Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 17 Apr 2024 16:43:23 +0200 Subject: [PATCH 015/189] wip --- include/ddc/kernels/splines/bsplines_non_uniform.hpp | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index 4a52c5d32..60d4dc400 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -24,7 +24,12 @@ struct NonUniformBSplinesBase { }; -/// NonUniformPointSampling specialization of BSplines +/** + * The type of a non-uniform BSplines 1D basis. + * + * @tparam Tag The tag identifying the continuous dimension which supports the building of the BSplines. + * @tparam D The degree of the BSplines. + */ template class NonUniformBSplines : NonUniformBSplinesBase { From ffef0b2a8f861fc806c92dfaca595579c3d14f5c Mon Sep 17 00:00:00 2001 From: blegouix Date: Thu, 18 Apr 2024 11:30:48 +0200 Subject: [PATCH 016/189] wip --- include/ddc/kernels/splines/bsplines_uniform.hpp | 13 +++++++++++-- include/ddc/kernels/splines/spline_builder.hpp | 4 +--- 2 files changed, 12 insertions(+), 5 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_uniform.hpp b/include/ddc/kernels/splines/bsplines_uniform.hpp index e6dd39963..f9571df4a 100644 --- a/include/ddc/kernels/splines/bsplines_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_uniform.hpp @@ -36,22 +36,25 @@ class UniformBSplines : UniformBSplinesBase static_assert(D > 0, "Parameter `D` must be positive"); public: + /// @brief The tag identifying the continuous dimension which supports the building of the BSplines. using tag_type = Tag; - + /// @brief The discrete dimension corresponding to BSplines. using discrete_dimension_type = UniformBSplines; -public: + /// @brief The rank. static constexpr std::size_t rank() { return 1; } + /// @brief The degree of BSplines. static constexpr std::size_t degree() noexcept { return D; } + /// @brief Indicates if the BSplines are periodic or not. static constexpr bool is_periodic() noexcept { return Tag::PERIODIC; @@ -67,6 +70,7 @@ class UniformBSplines : UniformBSplinesBase return true; } + /// @brief Impl template class Impl { @@ -221,6 +225,11 @@ struct is_uniform_bsplines : public std::is_base_of { }; +/** + * @brief Indicates if a dimension representing BSplines corresponds to uniform BSplines of not. + * + * @tparam The discrete dimension associated to BSplines + */ template constexpr bool is_uniform_bsplines_v = is_uniform_bsplines::value; diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index 7423b2aa8..1a150ea6f 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -17,9 +17,7 @@ namespace ddc { * An enum determining the backend solver of a SplineBuilder or SplineBuilder2d. Only GINKGO available at the moment, * other solvers will be implemented in the futur. */ -enum class SplineSolver { - GINKGO -}; +enum class SplineSolver { GINKGO }; /** * @brief An helper giving the uniform/non_uniform status of a spline interpolation mesh according to its attributes. From 2a050b073040b77b9c3ee4b8b5d19552846d283f Mon Sep 17 00:00:00 2001 From: blegouix Date: Thu, 18 Apr 2024 14:39:26 +0200 Subject: [PATCH 017/189] wip --- .../ddc/kernels/splines/bsplines_uniform.hpp | 96 +++++++++++++++++-- .../ddc/kernels/splines/spline_builder.hpp | 16 +--- 2 files changed, 94 insertions(+), 18 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_uniform.hpp b/include/ddc/kernels/splines/bsplines_uniform.hpp index f9571df4a..e12adf956 100644 --- a/include/ddc/kernels/splines/bsplines_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_uniform.hpp @@ -60,11 +60,13 @@ class UniformBSplines : UniformBSplinesBase return Tag::PERIODIC; } + /// @brief Indicates if the BSplines are radial or not (should be deprecated soon because this concept is not in the scope of DDC). static constexpr bool is_radial() noexcept { return false; } + /// @brief Indicates if the BSplines are uniform or not (this is obviously the case here). static constexpr bool is_uniform() noexcept { return true; @@ -84,20 +86,19 @@ class UniformBSplines : UniformBSplinesBase ddc::DiscreteDomain m_domain; public: + /// @brief The type of discrete dimension associated to BSplines. using discrete_dimension_type = UniformBSplines; + /// @brief The type of discrete domain indexing the BSplines. using discrete_domain_type = DiscreteDomain; + /// @brief The type of discrete element indexing a BSpline. using discrete_element_type = DiscreteElement; + /// @brief The type of discrete vector representing an "indexes displacement" between two BSplines. using discrete_vector_type = DiscreteVector; - Impl() = default; - - template - explicit Impl(Impl const& impl) : m_domain(impl.m_domain) - { - } + Impl() = default; /** Constructs a BSpline basis with n equidistant knots over \f$[a, b]\f$ * @@ -117,16 +118,33 @@ class UniformBSplines : UniformBSplinesBase mesh_type>(rmin, rmax, ddc::DiscreteVector(ncells + 1))); } + /// @brief Copy-constructs from another impl with different Kokkos memory space + template + explicit Impl(Impl const& impl) : m_domain(impl.m_domain) + { + } + + /// @brief Copy-constructs Impl(Impl const& x) = default; + /// @brief Move-constructs Impl(Impl&& x) = default; + /// @brief Destructs ~Impl() = default; + /// @brief Copy-assigns Impl& operator=(Impl const& x) = default; + /// @brief Move-assigns Impl& operator=(Impl&& x) = default; + /** @brief Evaluates BSplines at a given coordinate + * + * The values are computed for every BSplines at the given coordinate x. A spline approximation at coordinate x is a linear combination of those BSplines evaluations weigthed with splines coefficients of the spline-transformed initial discrete function. + * @param[out] values The values of the BSplines evaluated at coordinate x. It has to be a (1+degree) 1D mdspan. + * @param[in] x The coordinates where BSplines are evaluated. + */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_basis(DSpan1D values, ddc::Coordinate const& x) const { @@ -134,71 +152,135 @@ class UniformBSplines : UniformBSplinesBase return eval_basis(values, x, degree()); } + /** @brief Evaluates BSplines derivatives at a given coordinate + * + * The derivatives are computed for every BSplines at the given coordinate x. A spline approximation of a derivative at coordinate x is a linear combination of those BSplines derivatives weigthed with splines coefficients of the spline-transformed initial discrete function. + * @param[out] derivs The derivatives of the BSplines evaluated at coordinate x. It has to be a (1+degree) 1D mdspan. + * @param[in] x The coordinates where BSplines derivatives are evaluated. + */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_deriv(DSpan1D derivs, ddc::Coordinate const& x) const; + /** @brief Evaluates BSplines values and n derivatives at a given coordinate + * + * The values and derivatives are computed for every BSplines at the given coordinate x. + * @param[out] derivs The values and n derivatives of the BSplines evaluated at coordinate x. It has to be a (1+degree)*(1+n) 2D mdspan. + * @param[in] x The coordinates where BSplines derivatives are evaluated. + * @param[in] n The number of derivatives to evaluate (in addition to the BSplines values themselves). + */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_basis_and_n_derivs( ddc::DSpan2D derivs, ddc::Coordinate const& x, std::size_t n) const; + /** @brief Compute the integrals of the bsplines + * + * @param[out] int_vals The values of the integrals. It has to be a (1+nbasis) 1D mdspan. + */ template KOKKOS_INLINE_FUNCTION ddc::ChunkSpan integrals( ddc::ChunkSpan int_vals) const; + /** @brief Returns the coordinate of the knot corresponding to the given index for a BSpline. + * + * @param[in] idx Integer identifying index of the knot. + * @return Coordinate of the knot. + */ KOKKOS_INLINE_FUNCTION ddc::Coordinate get_knot(int idx) const noexcept { return ddc::Coordinate(rmin() + idx * ddc::step()); } + /** @brief Returns the first support knot associated to a discrete_element identifying a BSpline. + * + * @param[in] ix Index of the BSpline. + * @return Coordinate of the knot. + */ KOKKOS_INLINE_FUNCTION double get_first_support_knot(discrete_element_type const& ix) const { return get_knot(ix.uid() - degree()); } + /** @brief Returns the last support knot associated to a discrete_element identifying a BSpline. + * + * @param[in] ix Index of the BSpline. + * @return Coordinate of the knot. + */ KOKKOS_INLINE_FUNCTION double get_last_support_knot(discrete_element_type const& ix) const { return get_knot(ix.uid() + 1); } + /** @brief Returns the n-th knot associated to a discrete_element identifying a BSpline. + * + * @param[in] ix Index of the BSpline. + * @param[in] n Integer identifying a knot in the support of the BSpline. + */ KOKKOS_INLINE_FUNCTION double get_support_knot_n(discrete_element_type const& ix, int n) const { return get_knot(ix.uid() + n - degree()); } + /** @brief Returns the coordinate of the lower boundary BSpline. + * + * @return Coordinate of the lower boundary BSpline. + */ KOKKOS_INLINE_FUNCTION ddc::Coordinate rmin() const noexcept { return ddc::coordinate(m_domain.front()); } + /** @brief Returns the coordinate of the upper boundary BSpline. + * + * @return Coordinate of the upper boundary BSpline. + */ KOKKOS_INLINE_FUNCTION ddc::Coordinate rmax() const noexcept { return ddc::coordinate(m_domain.back()); } + /** @brief TODO + * + * @return TODO. + */ KOKKOS_INLINE_FUNCTION double length() const noexcept { return rmax() - rmin(); } + /** @brief TODO + * + * @return TODO. + */ KOKKOS_INLINE_FUNCTION std::size_t size() const noexcept { return degree() + ncells(); } - /// Returns the discrete domain including ghost bsplines + /** @brief Returns the discrete domain including ghost bsplines + * + * @return The discrete domain including ghost bsplines. + */ KOKKOS_INLINE_FUNCTION discrete_domain_type full_domain() const { return discrete_domain_type(discrete_element_type(0), discrete_vector_type(size())); } + /** @brief TODO + * + * @return TODO + */ KOKKOS_INLINE_FUNCTION std::size_t nbasis() const noexcept { return ncells() + !is_periodic() * degree(); } + /** @brief TODO + * + * @return TODO + */ KOKKOS_INLINE_FUNCTION std::size_t ncells() const noexcept { return m_domain.size() - 1; diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index 1a150ea6f..7c1824d69 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -249,25 +249,19 @@ class SplineBuilder preconditionner_max_block_size); } + /// @brief Copy-constructor is deleted SplineBuilder(SplineBuilder const& x) = delete; - /** - * @brief Create a new SplineBuilder by copy - * - * @param x The SplineBuilder being copied. - */ + /// @brief Move-constructs SplineBuilder(SplineBuilder&& x) = default; + /// @brief Destructs ~SplineBuilder() = default; + /// @brief Copy-assignment is deleted SplineBuilder& operator=(SplineBuilder const& x) = delete; - /** - * @brief Copy a SplineBuilder. - * - * @param x The SplineBuilder being copied. - * @returns A reference to this object. - */ + /// @brief Move-assigns SplineBuilder& operator=(SplineBuilder&& x) = default; /** From 880353bec833c10cff706b27778353c9b82c2c06 Mon Sep 17 00:00:00 2001 From: blegouix Date: Thu, 18 Apr 2024 14:47:24 +0200 Subject: [PATCH 018/189] bsplines --- .../kernels/splines/bsplines_non_uniform.hpp | 95 ++++++++++++++++++- 1 file changed, 92 insertions(+), 3 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index 680c081ab..20e6ca2d7 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -36,37 +36,43 @@ class NonUniformBSplines : NonUniformBSplinesBase static_assert(D > 0, "Parameter `D` must be positive"); public: + /// @brief The tag identifying the continuous dimension which supports the building of the BSplines. using tag_type = Tag; - + /// @brief The discrete dimension corresponding to BSplines. using discrete_dimension_type = NonUniformBSplines; -public: + /// @brief The rank. static constexpr std::size_t rank() { return 1; } + /// @brief The degree of BSplines. static constexpr std::size_t degree() noexcept { return D; } + /// @brief Indicates if the BSplines are periodic or not. static constexpr bool is_periodic() noexcept { return Tag::PERIODIC; } + /// @brief Indicates if the BSplines are radial or not (should be deprecated soon because this concept is not in the scope of DDC). static constexpr bool is_radial() noexcept { return false; } + /// @brief Indicates if the BSplines are uniform or not (this is obviously the case here). static constexpr bool is_uniform() noexcept { return false; } + /// @brief Impl template class Impl { @@ -81,12 +87,16 @@ class NonUniformBSplines : NonUniformBSplinesBase int m_nknots; public: + /// @brief The type of discrete dimension associated to BSplines. using discrete_dimension_type = NonUniformBSplines; + /// @brief The type of discrete domain indexing the BSplines. using discrete_domain_type = DiscreteDomain; + /// @brief The type of discrete element indexing a BSpline. using discrete_element_type = DiscreteElement; + /// @brief The type of discrete vector representing an "indexes displacement" between two BSplines. using discrete_vector_type = DiscreteVector; Impl() = default; @@ -114,49 +124,97 @@ class NonUniformBSplines : NonUniformBSplinesBase template Impl(RandomIt breaks_begin, RandomIt breaks_end); + /// @brief Copy-constructs Impl(Impl const& x) = default; + /// @brief Move-constructs Impl(Impl&& x) = default; + /// @brief Destructs ~Impl() = default; + /// @brief Copy-assigns Impl& operator=(Impl const& x) = default; + /// @brief Move-assigns Impl& operator=(Impl&& x) = default; + /** @brief Evaluates BSplines at a given coordinate + * + * The values are computed for every BSplines at the given coordinate x. A spline approximation at coordinate x is a linear combination of those BSplines evaluations weigthed with splines coefficients of the spline-transformed initial discrete function. + * @param[out] values The values of the BSplines evaluated at coordinate x. It has to be a (1+degree) 1D mdspan. + * @param[in] x The coordinates where BSplines are evaluated. + */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_basis(DSpan1D values, ddc::Coordinate const& x) const; + /** @brief Evaluates BSplines derivatives at a given coordinate + * + * The derivatives are computed for every BSplines at the given coordinate x. A spline approximation of a derivative at coordinate x is a linear combination of those BSplines derivatives weigthed with splines coefficients of the spline-transformed initial discrete function. + * @param[out] derivs The derivatives of the BSplines evaluated at coordinate x. It has to be a (1+degree) 1D mdspan. + * @param[in] x The coordinates where BSplines derivatives are evaluated. + */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_deriv(DSpan1D derivs, ddc::Coordinate const& x) const; + /** @brief Evaluates BSplines values and n derivatives at a given coordinate + * + * The values and derivatives are computed for every BSplines at the given coordinate x. + * @param[out] derivs The values and n derivatives of the BSplines evaluated at coordinate x. It has to be a (1+degree)*(1+n) 2D mdspan. + * @param[in] x The coordinates where BSplines derivatives are evaluated. + * @param[in] n The number of derivatives to evaluate (in addition to the BSplines values themselves). + */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_basis_and_n_derivs( ddc::DSpan2D derivs, ddc::Coordinate const& x, std::size_t n) const; + /** @brief Compute the integrals of the bsplines + * + * @param[out] int_vals The values of the integrals. It has to be a (1+nbasis) 1D mdspan. + */ template KOKKOS_INLINE_FUNCTION ddc::ChunkSpan integrals( ddc::ChunkSpan int_vals) const; + /** @brief Returns the coordinate of the knot corresponding to the given index for a BSpline. + * + * @param[in] idx Integer identifying index of the knot. + * @return Coordinate of the knot. + */ KOKKOS_INLINE_FUNCTION ddc::Coordinate get_knot(int knot_idx) const noexcept { return ddc::coordinate(ddc::DiscreteElement(knot_idx + degree())); } + /** @brief Returns the first support knot associated to a discrete_element identifying a BSpline. + * + * @param[in] ix Index of the BSpline. + * @return Coordinate of the knot. + */ KOKKOS_INLINE_FUNCTION ddc::Coordinate get_first_support_knot( discrete_element_type const& ix) const { return ddc::coordinate(ddc::DiscreteElement(ix.uid())); } + /** @brief Returns the last support knot associated to a discrete_element identifying a BSpline. + * + * @param[in] ix Index of the BSpline. + * @return Coordinate of the knot. + */ KOKKOS_INLINE_FUNCTION ddc::Coordinate get_last_support_knot( discrete_element_type const& ix) const { return ddc::coordinate(ddc::DiscreteElement(ix.uid() + degree() + 1)); } + /** @brief Returns the n-th knot associated to a discrete_element identifying a BSpline. + * + * @param[in] ix Index of the BSpline. + * @param[in] n Integer identifying a knot in the support of the BSpline. + */ KOKKOS_INLINE_FUNCTION ddc::Coordinate get_support_knot_n( discrete_element_type const& ix, int n) const @@ -164,42 +222,73 @@ class NonUniformBSplines : NonUniformBSplinesBase return ddc::coordinate(ddc::DiscreteElement(ix.uid() + n)); } + /** @brief Returns the coordinate of the lower boundary BSpline. + * + * @return Coordinate of the lower boundary BSpline. + */ KOKKOS_INLINE_FUNCTION ddc::Coordinate rmin() const noexcept { return get_knot(0); } + /** @brief Returns the coordinate of the upper boundary BSpline. + * + * @return Coordinate of the upper boundary BSpline. + */ KOKKOS_INLINE_FUNCTION ddc::Coordinate rmax() const noexcept { return get_knot(ncells()); } + /** @brief TODO + * + * @return TODO. + */ KOKKOS_INLINE_FUNCTION double length() const noexcept { return rmax() - rmin(); } + /** @brief TODO + * + * @return TODO. + */ KOKKOS_INLINE_FUNCTION std::size_t size() const noexcept { return degree() + ncells(); } - /// Returns the discrete domain including ghost bsplines + /** @brief Returns the discrete domain including ghost bsplines + * + * @return The discrete domain including ghost bsplines. + */ KOKKOS_INLINE_FUNCTION discrete_domain_type full_domain() const { return discrete_domain_type(discrete_element_type(0), discrete_vector_type(size())); } + /** @brief TODO + * + * @return TODO + */ KOKKOS_INLINE_FUNCTION std::size_t npoints() const noexcept { return m_nknots - 2 * degree(); } + /** @brief TODO + * + * @return TODO + */ KOKKOS_INLINE_FUNCTION std::size_t nbasis() const noexcept { return ncells() + !is_periodic() * degree(); } + /** @brief TODO + * + * @return TODO + */ KOKKOS_INLINE_FUNCTION std::size_t ncells() const noexcept { return npoints() - 1; From 39f2d7092f3fbe53612fe9b0b1cae447a8325060 Mon Sep 17 00:00:00 2001 From: blegouix Date: Thu, 18 Apr 2024 14:49:22 +0200 Subject: [PATCH 019/189] init --- .../ddc/kernels/splines/spline_builder.hpp | 236 +++++++++++++----- .../ddc/kernels/splines/spline_builder_2d.hpp | 179 ++++++++----- 2 files changed, 289 insertions(+), 126 deletions(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index e30e87b23..7c1824d69 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -10,10 +10,24 @@ #include "deriv.hpp" namespace ddc { -enum class SplineSolver { - GINKGO -}; // Only GINKGO available atm, other solvers will be implemented in the futur +/** + * @brief An enum determining the backend solver of a SplineBuilder or SplineBuilder2d. + * + * An enum determining the backend solver of a SplineBuilder or SplineBuilder2d. Only GINKGO available at the moment, + * other solvers will be implemented in the futur. + */ +enum class SplineSolver { GINKGO }; + +/** + * @brief An helper giving the uniform/non_uniform status of a spline interpolation mesh according to its attributes. + * + * An helper giving the uniform/non_uniform status of a spline interpolation mesh according to its attributes. + * @param is_uniform A boolean giving the presumed status before considering boundary conditions. + * @param BcXmin The lower boundary condition. + * @param BcXmax The upper boundary condition. + * @param int The degree of the spline. + */ constexpr bool is_spline_interpolation_mesh_uniform( bool const is_uniform, ddc::BoundCond const BcXmin, @@ -34,6 +48,14 @@ constexpr bool is_spline_interpolation_mesh_uniform( * of BSplines. The spline is constructed such that it respects the boundary conditions * BcXmin and BcXmax, and it interpolates the function at the points on the interpolation_mesh * associated with interpolation_mesh_type. + * @tparam ExecSpace The Kokkos execution space on which the spline transform is performed. + * @tparam MemorySpace The Kokkos memory space on which the data (interpolation function and splines coefficients) are stored. + * @tparam BSplines The discrete dimension representing the BSplines. + * @tparam InterpolationMesh The discrete dimension supporting the interpolation points. + * @tparam BcXmin The lower boundary condition. + * @tparam BcXmax The upper boundary condition. + * @tparam Solver The SplineSolver giving the backend used to perform the spline transform. + * @tparam IDimX A variadic template of all the discrete dimensions forming the full space (InterpolationMesh + batched dimensions). */ template < class ExecSpace, @@ -57,52 +79,79 @@ class SplineBuilder using tag_type = typename InterpolationMesh::continuous_dimension_type; public: + /** + * @brief The type of the Kokkos execution space used by this class. + */ using exec_space = ExecSpace; + /** + * @brief The type of the Kokkos memory space used by this class. + */ using memory_space = MemorySpace; /** - * @brief The type of the interpolation mesh used by this class. + * @brief The type of the interpolation discrete dimension (discrete dimension of interest) used by this class. */ using interpolation_mesh_type = InterpolationMesh; /** - * @brief The type of the BSplines which are compatible with this class. + * @brief The discrete dimension representing the BSplines. */ using bsplines_type = BSplines; + /** + * @brief The Deriv dimension at the boundaries. + */ using deriv_type = ddc::Deriv; /** - * @brief The type of the domain for the interpolation mesh used by this class. + * @brief The type of the domain for the 1D interpolation mesh used by this class. */ using interpolation_domain_type = ddc::DiscreteDomain; - using vals_domain_type = ddc::DiscreteDomain; + /** + * @brief The type of the whole domain representing interpolation points. + */ + using batched_interpolation_domain_type = ddc::DiscreteDomain; + /** + * @brief The type of the batch domain (obtained by removing dimension of interest from whole space). + */ using batch_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq>>; + /** + * @brief Helper to get the dimension of batched_spline_domain_type associated to a dimension of batched_interpolation_domain_type. + */ template using spline_dim_type = std::conditional_t, bsplines_type, Tag>; - using spline_domain_type = + /** + * @brief The type of the whole spline domain (cartesian product of 1D spline domain and batch domain) preserving the underlying memory layout (order of dimensions). + */ + using batched_spline_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq, ddc::detail::TypeSeq>>; - using spline_tr_domain_type = + /** + * @brief The type of the whole spline domain (cartesian product of 1D spline domain and batch domain) with 1D spline domain being contiguous . + */ + using batched_spline_tr_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, ddc::type_seq_remove_t< ddc::detail::TypeSeq, ddc::detail::TypeSeq>>>; - using derivs_domain_type = + /** + * @brief The type of the whole Derivs domain (cartesian product of 1D Deriv domain and batch domain) preserving the underlying memory layout (order of dimensions). + */ + using batched_derivs_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq, @@ -114,12 +163,12 @@ class SplineBuilder static constexpr bool s_odd = BSplines::degree() % 2; /** - * @brief The number of equations which define the boundary conditions at the lower bound. + * @brief The number of equations defining the boundary conditions at the lower bound. */ static constexpr int s_nbe_xmin = n_boundary_equations(BcXmin, BSplines::degree()); /** - * @brief The number of equations which define the boundary conditions at the upper bound. + * @brief The number of equations defining the boundary conditions at the upper bound. */ static constexpr int s_nbe_xmax = n_boundary_equations(BcXmax, BSplines::degree()); @@ -152,7 +201,7 @@ class SplineBuilder static constexpr ddc::BoundCond s_bc_xmax = BcXmax; private: - vals_domain_type m_vals_domain; + batched_interpolation_domain_type m_batched_interpolation_domain; int m_offset; @@ -162,13 +211,22 @@ class SplineBuilder std::unique_ptr matrix; public: + /** + * @brief An helper to compute the offset. + */ int compute_offset(interpolation_domain_type const& interpolation_domain); + /** + * @brief Build a SplineBuilder acting on batched_interpolation_domain. + * + * @param batched_interpolation_domain The domain on which are defined the interpolation points. + * @param cols_per_chunk An hyperparameter used by the slicer (internal to the solver) to define the size of a chunk of right-and-sides of the linear problem to be computed in parallel. + */ explicit SplineBuilder( - vals_domain_type const& vals_domain, + batched_interpolation_domain_type const& batched_interpolation_domain, std::optional cols_per_chunk = std::nullopt, std::optional preconditionner_max_block_size = std::nullopt) - : m_vals_domain(vals_domain) + : m_batched_interpolation_domain(batched_interpolation_domain) , m_offset(compute_offset(interpolation_domain())) , m_dx((ddc::discrete_space().rmax() - ddc::discrete_space().rmin()) / ddc::discrete_space().ncells()) @@ -191,88 +249,123 @@ class SplineBuilder preconditionner_max_block_size); } + /// @brief Copy-constructor is deleted SplineBuilder(SplineBuilder const& x) = delete; - /** - * @brief Create a new SplineBuilder by copy - * - * @param x The SplineBuilder being copied. - */ + /// @brief Move-constructs SplineBuilder(SplineBuilder&& x) = default; + /// @brief Destructs ~SplineBuilder() = default; + /// @brief Copy-assignment is deleted SplineBuilder& operator=(SplineBuilder const& x) = delete; + /// @brief Move-assigns + SplineBuilder& operator=(SplineBuilder&& x) = default; + /** - * @brief Copy a SplineBuilder. + * @brief Get the domain for the 1D interpolation mesh used by this class. * - * @param x The SplineBuilder being copied. - * @returns A reference to this object. + * Get the 1D interpolation domain associated to dimension of interest. + * + * @return The 1D domain for the grid points. */ - SplineBuilder& operator=(SplineBuilder&& x) = default; - - vals_domain_type vals_domain() const noexcept + interpolation_domain_type interpolation_domain() const noexcept { - return m_vals_domain; + return interpolation_domain_type(m_batched_interpolation_domain); } /** - * @brief Get the domain from which the approximation is defined. + * @brief Get the whole domain representing interpolation points. * * Get the domain on which values of the function must be provided in order - * to build a spline approximation of the function. + * to build a spline transform of the function. * * @return The domain for the grid points. */ - interpolation_domain_type interpolation_domain() const noexcept + batched_interpolation_domain_type batched_interpolation_domain() const noexcept { - return interpolation_domain_type(vals_domain()); + return m_batched_interpolation_domain; } + /** + * @brief Get the batch domain. + * + * Get the batch domain (obtained by removing dimension of interest from whole interpolation domain). + * + * @return The batch domain. + */ batch_domain_type batch_domain() const noexcept { - return ddc::remove_dims_of(vals_domain(), interpolation_domain()); + return ddc::remove_dims_of(batched_interpolation_domain(), interpolation_domain()); } - ddc::DiscreteDomain bsplines_domain() const noexcept // TODO : clarify name + /** + * @brief Get the 1D domain on which spline coefficients are defined. + * + * Get the 1D spline domain corresponding to dimension of interest. + * + * @return The 1D domain for the spline coefficients. + */ + ddc::DiscreteDomain spline_domain() const noexcept { return ddc::discrete_space().full_domain(); } /** - * @brief Get the domain on which the approximation is defined. + * @brief Get the whole domain on which spline coefficients are defined, preserving memory layout. * - * Get the domain of the basis-splines for which the coefficients of the spline - * approximation must be calculated. + * Get the whole domain on which spline coefficients will be computed, preserving memory layout (order of dimensions). * - * @return The domain for the splines. + * @return The domain for the spline coefficients. */ - spline_domain_type spline_domain() const noexcept + batched_spline_domain_type batched_spline_domain() const noexcept { return ddc::replace_dim_of< interpolation_mesh_type, - bsplines_type>(vals_domain(), bsplines_domain()); + bsplines_type>(batched_interpolation_domain(), spline_domain()); } - spline_tr_domain_type spline_tr_domain() const noexcept + /** + * @brief Get the whole domain on which spline coefficients are defined, with dimension of interest contiguous. + * + * Get the (transposed) whole domain on which spline coefficients will be computed, with dimension of interest contiguous. + * + * @return The (transposed) domain for the spline coefficients. + */ + batched_spline_tr_domain_type batched_spline_tr_domain() const noexcept { - return spline_tr_domain_type(bsplines_domain(), batch_domain()); + return batched_spline_tr_domain_type(spline_domain(), batch_domain()); } - derivs_domain_type derivs_xmin_domain() const noexcept + /** + * @brief Get the whole domain on which derivatives on lower boundary are defined. + * + * Get the whole domain on which derivatives on lower boundary are defined. This is used only with HERMITE boundary conditions. + * + * @return The domain for the Derivs values. + */ + batched_derivs_domain_type batched_derivs_xmin_domain() const noexcept { return ddc::replace_dim_of( - vals_domain(), + batched_interpolation_domain(), ddc::DiscreteDomain( ddc::DiscreteElement(1), ddc::DiscreteVector(s_nbc_xmin))); } - derivs_domain_type derivs_xmax_domain() const noexcept + /** + * @brief Get the whole domain on which derivatives on upper boundary are defined. + * + * Get the whole domain on which derivatives on upper boundary are defined. This is used only with HERMITE boundary conditions. + * + * @return The domain for the Derivs values. + */ + batched_derivs_domain_type batched_derivs_xmax_domain() const noexcept { return ddc::replace_dim_of( - vals_domain(), + batched_interpolation_domain(), ddc::DiscreteDomain( ddc::DiscreteElement(1), ddc::DiscreteVector(s_nbc_xmax))); @@ -283,6 +376,10 @@ class SplineBuilder * * Get the interpolation matrix. This can be useful for debugging (as it allows * one to print the matrix) or for more complex quadrature schemes. + * + * Warning: the returned ddc::detail::Matrix class is not supposed to be exposed + * to user, which means its usage is not tested out of the scope of DDC splines transforms. + * Use at your own risk. * * @return A reference to the interpolation matrix. */ @@ -304,20 +401,27 @@ class SplineBuilder * * @param[out] spline The coefficients of the spline calculated by the function. * @param[in] vals The values of the function at the grid points. - * @param[in] derivs_xmin The values of the derivatives at the lower boundary. - * @param[in] derivs_xmax The values of the derivatives at the upper boundary. + * @param[in] derivs_xmin The values of the derivatives at the lower boundary + * (used only with HERMITE lower boundary condition). + * @param[in] derivs_xmax The values of the derivatives at the upper boundary + * (used only with HERMITE upper boundary condition). */ template void operator()( - ddc::ChunkSpan spline, - ddc::ChunkSpan vals, - std::optional< - ddc::ChunkSpan> const - derivs_xmin + ddc::ChunkSpan spline, + ddc::ChunkSpan + vals, + std::optional> const derivs_xmin = std::nullopt, - std::optional< - ddc::ChunkSpan> const - derivs_xmax + std::optional> const derivs_xmax = std::nullopt) const; private: @@ -638,12 +742,18 @@ void SplineBuilder< Solver, IDimX...>:: operator()( - ddc::ChunkSpan spline, - ddc::ChunkSpan vals, - std::optional> const - derivs_xmin, - std::optional> const - derivs_xmax) const + ddc::ChunkSpan spline, + ddc::ChunkSpan vals, + std::optional> const derivs_xmin, + std::optional> const derivs_xmax) const { assert(vals.template extent() == ddc::discrete_space().nbasis() - s_nbe_xmin - s_nbe_xmax); @@ -718,7 +828,9 @@ operator()( // TODO : Consider optimizing // Allocate and fill a transposed version of spline in order to get dimension of interest as last dimension (optimal for GPU, necessary for Ginkgo) - ddc::Chunk spline_tr_alloc(spline_tr_domain(), ddc::KokkosAllocator()); + ddc::Chunk spline_tr_alloc( + batched_spline_tr_domain(), + ddc::KokkosAllocator()); ddc::ChunkSpan spline_tr = spline_tr_alloc.span_view(); ddc::parallel_for_each( exec_space(), diff --git a/include/ddc/kernels/splines/spline_builder_2d.hpp b/include/ddc/kernels/splines/spline_builder_2d.hpp index 372954e96..872bf2956 100644 --- a/include/ddc/kernels/splines/spline_builder_2d.hpp +++ b/include/ddc/kernels/splines/spline_builder_2d.hpp @@ -87,7 +87,14 @@ class SplineBuilder2D */ using bsplines_type2 = typename builder_type2::bsplines_type; + /** + * @brief The type of the Deriv domain on boundaries in the first dimension which are compatible with this class. + */ using deriv_type1 = typename builder_type1::deriv_type; + + /** + * @brief The type of the Deriv domain on boundaries in the second dimension which are compatible with this class. + */ using deriv_type2 = typename builder_type2::deriv_type; /** @@ -113,26 +120,26 @@ class SplineBuilder2D using interpolation_domain_type = ddc::DiscreteDomain; - using vals_domain_type = ddc::DiscreteDomain; + using batched_interpolation_domain_type = ddc::DiscreteDomain; using batch_domain_type = ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq>>; - using spline_domain_type + using batched_spline_domain_type = ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq, ddc::detail::TypeSeq>>; - using derivs_domain_type1 = typename builder_type1::derivs_domain_type; - using derivs_domain_type2 + using batched_derivs_domain_type1 = typename builder_type1::batched_derivs_domain_type; + using batched_derivs_domain_type2 = ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq, ddc::detail::TypeSeq>>; - using derivs_domain_type + using batched_derivs_domain_type = ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq, @@ -147,24 +154,27 @@ class SplineBuilder2D /** * @brief Create a new SplineBuilder2D. * - * @param vals_domain + * @param batched_interpolation_domain * The 2D domain on which points will be provided in order to * create the 2D spline approximation. * @param cols_per_chunk The number of columns in the rhs passed to the underlying linear solver. * @param preconditionner_max_block_size The block size of in the block Jacobi preconditioner. */ explicit SplineBuilder2D( - vals_domain_type const& vals_domain, + batched_interpolation_domain_type const& batched_interpolation_domain, std::optional cols_per_chunk = std::nullopt, std::optional preconditionner_max_block_size = std::nullopt) - : m_spline_builder1(vals_domain, cols_per_chunk, preconditionner_max_block_size) + : m_spline_builder1( + batched_interpolation_domain, + cols_per_chunk, + preconditionner_max_block_size) , m_spline_builder_deriv1(ddc::replace_dim_of( - m_spline_builder1.vals_domain(), + m_spline_builder1.batched_interpolation_domain(), ddc::DiscreteDomain( ddc::DiscreteElement(1), ddc::DiscreteVector(bsplines_type2::degree() / 2)))) , m_spline_builder2( - m_spline_builder1.spline_domain(), + m_spline_builder1.batched_spline_domain(), cols_per_chunk, preconditionner_max_block_size) { @@ -200,9 +210,9 @@ class SplineBuilder2D */ SplineBuilder2D& operator=(SplineBuilder2D&& x) = default; - vals_domain_type vals_domain() const noexcept + batched_interpolation_domain_type batched_interpolation_domain() const noexcept { - return m_spline_builder1.vals_domain(); + return m_spline_builder1.batched_interpolation_domain(); } /** @@ -222,7 +232,7 @@ class SplineBuilder2D batch_domain_type batch_domain() const noexcept { - return ddc::remove_dims_of(vals_domain(), interpolation_domain()); + return ddc::remove_dims_of(batched_interpolation_domain(), interpolation_domain()); } /** @@ -233,7 +243,7 @@ class SplineBuilder2D * * @return The 2D domain for the splines. */ - ddc::DiscreteDomain bsplines_domain() + ddc::DiscreteDomain spline_domain() const noexcept // TODO : clarify name { return ddc::DiscreteDomain( @@ -241,13 +251,13 @@ class SplineBuilder2D ddc::discrete_space().full_domain()); } - spline_domain_type spline_domain() const noexcept + batched_spline_domain_type batched_spline_domain() const noexcept { return ddc::replace_dim_of( ddc::replace_dim_of< interpolation_mesh_type2, - bsplines_type2>(vals_domain(), bsplines_domain()), - bsplines_domain()); + bsplines_type2>(batched_interpolation_domain(), spline_domain()), + spline_domain()); } /** @@ -288,39 +298,56 @@ class SplineBuilder2D */ template void operator()( - ddc::ChunkSpan spline, - ddc::ChunkSpan vals, - std::optional< - ddc::ChunkSpan> const - derivs_min1 + ddc::ChunkSpan spline, + ddc::ChunkSpan + vals, + std::optional> const derivs_min1 = std::nullopt, - std::optional< - ddc::ChunkSpan> const - derivs_max1 + std::optional> const derivs_max1 = std::nullopt, - std::optional< - ddc::ChunkSpan> const - derivs_min2 + std::optional> const derivs_min2 = std::nullopt, - std::optional< - ddc::ChunkSpan> const - derivs_max2 + std::optional> const derivs_max2 = std::nullopt, - std::optional< - ddc::ChunkSpan> const - mixed_derivs_min1_min2 + std::optional> const mixed_derivs_min1_min2 = std::nullopt, - std::optional< - ddc::ChunkSpan> const - mixed_derivs_max1_min2 + std::optional> const mixed_derivs_max1_min2 = std::nullopt, - std::optional< - ddc::ChunkSpan> const - mixed_derivs_min1_max2 + std::optional> const mixed_derivs_min1_max2 = std::nullopt, - std::optional< - ddc::ChunkSpan> const - mixed_derivs_max1_max2 + std::optional> const mixed_derivs_max1_max2 = std::nullopt) const; }; @@ -353,29 +380,53 @@ void SplineBuilder2D< Solver, IDimX...>:: operator()( - ddc::ChunkSpan spline, - ddc::ChunkSpan vals, - std::optional> const - derivs_min1, - std::optional> const - derivs_max1, - std::optional> const - derivs_min2, - std::optional> const - derivs_max2, - std::optional> const - mixed_derivs_min1_min2, - std::optional> const - mixed_derivs_max1_min2, - std::optional> const - mixed_derivs_min1_max2, - std::optional> const - mixed_derivs_max1_max2) const + ddc::ChunkSpan spline, + ddc::ChunkSpan vals, + std::optional> const derivs_min1, + std::optional> const derivs_max1, + std::optional> const derivs_min2, + std::optional> const derivs_max2, + std::optional> const mixed_derivs_min1_min2, + std::optional> const mixed_derivs_max1_min2, + std::optional> const mixed_derivs_min1_max2, + std::optional> const mixed_derivs_max1_max2) const { // TODO: perform computations along dimension 1 on different streams ? // Spline1-transform derivs_min2 (to spline1_deriv_min) ddc::Chunk spline1_deriv_min_alloc( - m_spline_builder_deriv1.spline_domain(), + m_spline_builder_deriv1.batched_spline_domain(), ddc::KokkosAllocator()); auto spline1_deriv_min = spline1_deriv_min_alloc.span_view(); auto spline1_deriv_min_opt = std::optional(spline1_deriv_min.span_cview()); @@ -391,7 +442,7 @@ operator()( // Spline1-transform vals (to spline1) ddc::Chunk spline1_alloc( - m_spline_builder1.spline_domain(), + m_spline_builder1.batched_spline_domain(), ddc::KokkosAllocator()); ddc::ChunkSpan spline1 = spline1_alloc.span_view(); @@ -399,7 +450,7 @@ operator()( // Spline1-transform derivs_max2 (to spline1_deriv_max) ddc::Chunk spline1_deriv_max_alloc( - m_spline_builder_deriv1.spline_domain(), + m_spline_builder_deriv1.batched_spline_domain(), ddc::KokkosAllocator()); auto spline1_deriv_max = spline1_deriv_max_alloc.span_view(); auto spline1_deriv_max_opt = std::optional(spline1_deriv_max.span_cview()); From c0ef4587d7d7510671f0d53815b0d7071bfafe89 Mon Sep 17 00:00:00 2001 From: blegouix Date: Thu, 18 Apr 2024 14:51:08 +0200 Subject: [PATCH 020/189] reinit --- .../kernels/splines/bsplines_non_uniform.hpp | 102 +++++++- .../ddc/kernels/splines/bsplines_uniform.hpp | 115 ++++++++- .../ddc/kernels/splines/spline_builder.hpp | 236 +++++------------- .../ddc/kernels/splines/spline_builder_2d.hpp | 179 +++++-------- 4 files changed, 330 insertions(+), 302 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index 0715564d7..20e6ca2d7 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -24,44 +24,55 @@ struct NonUniformBSplinesBase { }; -/// NonUniformPointSampling specialization of BSplines +/** + * The type of a non-uniform BSplines 1D basis. + * + * @tparam Tag The tag identifying the continuous dimension which supports the building of the BSplines. + * @tparam D The degree of the BSplines. + */ template class NonUniformBSplines : NonUniformBSplinesBase { static_assert(D > 0, "Parameter `D` must be positive"); public: + /// @brief The tag identifying the continuous dimension which supports the building of the BSplines. using tag_type = Tag; - + /// @brief The discrete dimension corresponding to BSplines. using discrete_dimension_type = NonUniformBSplines; -public: + /// @brief The rank. static constexpr std::size_t rank() { return 1; } + /// @brief The degree of BSplines. static constexpr std::size_t degree() noexcept { return D; } + /// @brief Indicates if the BSplines are periodic or not. static constexpr bool is_periodic() noexcept { return Tag::PERIODIC; } + /// @brief Indicates if the BSplines are radial or not (should be deprecated soon because this concept is not in the scope of DDC). static constexpr bool is_radial() noexcept { return false; } + /// @brief Indicates if the BSplines are uniform or not (this is obviously the case here). static constexpr bool is_uniform() noexcept { return false; } + /// @brief Impl template class Impl { @@ -76,12 +87,16 @@ class NonUniformBSplines : NonUniformBSplinesBase int m_nknots; public: + /// @brief The type of discrete dimension associated to BSplines. using discrete_dimension_type = NonUniformBSplines; + /// @brief The type of discrete domain indexing the BSplines. using discrete_domain_type = DiscreteDomain; + /// @brief The type of discrete element indexing a BSpline. using discrete_element_type = DiscreteElement; + /// @brief The type of discrete vector representing an "indexes displacement" between two BSplines. using discrete_vector_type = DiscreteVector; Impl() = default; @@ -109,49 +124,97 @@ class NonUniformBSplines : NonUniformBSplinesBase template Impl(RandomIt breaks_begin, RandomIt breaks_end); + /// @brief Copy-constructs Impl(Impl const& x) = default; + /// @brief Move-constructs Impl(Impl&& x) = default; + /// @brief Destructs ~Impl() = default; + /// @brief Copy-assigns Impl& operator=(Impl const& x) = default; + /// @brief Move-assigns Impl& operator=(Impl&& x) = default; + /** @brief Evaluates BSplines at a given coordinate + * + * The values are computed for every BSplines at the given coordinate x. A spline approximation at coordinate x is a linear combination of those BSplines evaluations weigthed with splines coefficients of the spline-transformed initial discrete function. + * @param[out] values The values of the BSplines evaluated at coordinate x. It has to be a (1+degree) 1D mdspan. + * @param[in] x The coordinates where BSplines are evaluated. + */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_basis(DSpan1D values, ddc::Coordinate const& x) const; + /** @brief Evaluates BSplines derivatives at a given coordinate + * + * The derivatives are computed for every BSplines at the given coordinate x. A spline approximation of a derivative at coordinate x is a linear combination of those BSplines derivatives weigthed with splines coefficients of the spline-transformed initial discrete function. + * @param[out] derivs The derivatives of the BSplines evaluated at coordinate x. It has to be a (1+degree) 1D mdspan. + * @param[in] x The coordinates where BSplines derivatives are evaluated. + */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_deriv(DSpan1D derivs, ddc::Coordinate const& x) const; + /** @brief Evaluates BSplines values and n derivatives at a given coordinate + * + * The values and derivatives are computed for every BSplines at the given coordinate x. + * @param[out] derivs The values and n derivatives of the BSplines evaluated at coordinate x. It has to be a (1+degree)*(1+n) 2D mdspan. + * @param[in] x The coordinates where BSplines derivatives are evaluated. + * @param[in] n The number of derivatives to evaluate (in addition to the BSplines values themselves). + */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_basis_and_n_derivs( ddc::DSpan2D derivs, ddc::Coordinate const& x, std::size_t n) const; + /** @brief Compute the integrals of the bsplines + * + * @param[out] int_vals The values of the integrals. It has to be a (1+nbasis) 1D mdspan. + */ template KOKKOS_INLINE_FUNCTION ddc::ChunkSpan integrals( ddc::ChunkSpan int_vals) const; + /** @brief Returns the coordinate of the knot corresponding to the given index for a BSpline. + * + * @param[in] idx Integer identifying index of the knot. + * @return Coordinate of the knot. + */ KOKKOS_INLINE_FUNCTION ddc::Coordinate get_knot(int knot_idx) const noexcept { return ddc::coordinate(ddc::DiscreteElement(knot_idx + degree())); } + /** @brief Returns the first support knot associated to a discrete_element identifying a BSpline. + * + * @param[in] ix Index of the BSpline. + * @return Coordinate of the knot. + */ KOKKOS_INLINE_FUNCTION ddc::Coordinate get_first_support_knot( discrete_element_type const& ix) const { return ddc::coordinate(ddc::DiscreteElement(ix.uid())); } + /** @brief Returns the last support knot associated to a discrete_element identifying a BSpline. + * + * @param[in] ix Index of the BSpline. + * @return Coordinate of the knot. + */ KOKKOS_INLINE_FUNCTION ddc::Coordinate get_last_support_knot( discrete_element_type const& ix) const { return ddc::coordinate(ddc::DiscreteElement(ix.uid() + degree() + 1)); } + /** @brief Returns the n-th knot associated to a discrete_element identifying a BSpline. + * + * @param[in] ix Index of the BSpline. + * @param[in] n Integer identifying a knot in the support of the BSpline. + */ KOKKOS_INLINE_FUNCTION ddc::Coordinate get_support_knot_n( discrete_element_type const& ix, int n) const @@ -159,42 +222,73 @@ class NonUniformBSplines : NonUniformBSplinesBase return ddc::coordinate(ddc::DiscreteElement(ix.uid() + n)); } + /** @brief Returns the coordinate of the lower boundary BSpline. + * + * @return Coordinate of the lower boundary BSpline. + */ KOKKOS_INLINE_FUNCTION ddc::Coordinate rmin() const noexcept { return get_knot(0); } + /** @brief Returns the coordinate of the upper boundary BSpline. + * + * @return Coordinate of the upper boundary BSpline. + */ KOKKOS_INLINE_FUNCTION ddc::Coordinate rmax() const noexcept { return get_knot(ncells()); } + /** @brief TODO + * + * @return TODO. + */ KOKKOS_INLINE_FUNCTION double length() const noexcept { return rmax() - rmin(); } + /** @brief TODO + * + * @return TODO. + */ KOKKOS_INLINE_FUNCTION std::size_t size() const noexcept { return degree() + ncells(); } - /// Returns the discrete domain including ghost bsplines + /** @brief Returns the discrete domain including ghost bsplines + * + * @return The discrete domain including ghost bsplines. + */ KOKKOS_INLINE_FUNCTION discrete_domain_type full_domain() const { return discrete_domain_type(discrete_element_type(0), discrete_vector_type(size())); } + /** @brief TODO + * + * @return TODO + */ KOKKOS_INLINE_FUNCTION std::size_t npoints() const noexcept { return m_nknots - 2 * degree(); } + /** @brief TODO + * + * @return TODO + */ KOKKOS_INLINE_FUNCTION std::size_t nbasis() const noexcept { return ncells() + !is_periodic() * degree(); } + /** @brief TODO + * + * @return TODO + */ KOKKOS_INLINE_FUNCTION std::size_t ncells() const noexcept { return npoints() - 1; diff --git a/include/ddc/kernels/splines/bsplines_uniform.hpp b/include/ddc/kernels/splines/bsplines_uniform.hpp index c654e482a..e12adf956 100644 --- a/include/ddc/kernels/splines/bsplines_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_uniform.hpp @@ -24,43 +24,55 @@ struct UniformBSplinesBase { }; +/** + * The type of a uniform BSplines 1D basis. + * + * @tparam Tag The tag identifying the continuous dimension which supports the building of the BSplines. + * @tparam D The degree of the BSplines. + */ template class UniformBSplines : UniformBSplinesBase { static_assert(D > 0, "Parameter `D` must be positive"); public: + /// @brief The tag identifying the continuous dimension which supports the building of the BSplines. using tag_type = Tag; - + /// @brief The discrete dimension corresponding to BSplines. using discrete_dimension_type = UniformBSplines; -public: + /// @brief The rank. static constexpr std::size_t rank() { return 1; } + /// @brief The degree of BSplines. static constexpr std::size_t degree() noexcept { return D; } + /// @brief Indicates if the BSplines are periodic or not. static constexpr bool is_periodic() noexcept { return Tag::PERIODIC; } + /// @brief Indicates if the BSplines are radial or not (should be deprecated soon because this concept is not in the scope of DDC). static constexpr bool is_radial() noexcept { return false; } + /// @brief Indicates if the BSplines are uniform or not (this is obviously the case here). static constexpr bool is_uniform() noexcept { return true; } + /// @brief Impl template class Impl { @@ -74,20 +86,19 @@ class UniformBSplines : UniformBSplinesBase ddc::DiscreteDomain m_domain; public: + /// @brief The type of discrete dimension associated to BSplines. using discrete_dimension_type = UniformBSplines; + /// @brief The type of discrete domain indexing the BSplines. using discrete_domain_type = DiscreteDomain; + /// @brief The type of discrete element indexing a BSpline. using discrete_element_type = DiscreteElement; + /// @brief The type of discrete vector representing an "indexes displacement" between two BSplines. using discrete_vector_type = DiscreteVector; - Impl() = default; - - template - explicit Impl(Impl const& impl) : m_domain(impl.m_domain) - { - } + Impl() = default; /** Constructs a BSpline basis with n equidistant knots over \f$[a, b]\f$ * @@ -107,16 +118,33 @@ class UniformBSplines : UniformBSplinesBase mesh_type>(rmin, rmax, ddc::DiscreteVector(ncells + 1))); } + /// @brief Copy-constructs from another impl with different Kokkos memory space + template + explicit Impl(Impl const& impl) : m_domain(impl.m_domain) + { + } + + /// @brief Copy-constructs Impl(Impl const& x) = default; + /// @brief Move-constructs Impl(Impl&& x) = default; + /// @brief Destructs ~Impl() = default; + /// @brief Copy-assigns Impl& operator=(Impl const& x) = default; + /// @brief Move-assigns Impl& operator=(Impl&& x) = default; + /** @brief Evaluates BSplines at a given coordinate + * + * The values are computed for every BSplines at the given coordinate x. A spline approximation at coordinate x is a linear combination of those BSplines evaluations weigthed with splines coefficients of the spline-transformed initial discrete function. + * @param[out] values The values of the BSplines evaluated at coordinate x. It has to be a (1+degree) 1D mdspan. + * @param[in] x The coordinates where BSplines are evaluated. + */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_basis(DSpan1D values, ddc::Coordinate const& x) const { @@ -124,71 +152,135 @@ class UniformBSplines : UniformBSplinesBase return eval_basis(values, x, degree()); } + /** @brief Evaluates BSplines derivatives at a given coordinate + * + * The derivatives are computed for every BSplines at the given coordinate x. A spline approximation of a derivative at coordinate x is a linear combination of those BSplines derivatives weigthed with splines coefficients of the spline-transformed initial discrete function. + * @param[out] derivs The derivatives of the BSplines evaluated at coordinate x. It has to be a (1+degree) 1D mdspan. + * @param[in] x The coordinates where BSplines derivatives are evaluated. + */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_deriv(DSpan1D derivs, ddc::Coordinate const& x) const; + /** @brief Evaluates BSplines values and n derivatives at a given coordinate + * + * The values and derivatives are computed for every BSplines at the given coordinate x. + * @param[out] derivs The values and n derivatives of the BSplines evaluated at coordinate x. It has to be a (1+degree)*(1+n) 2D mdspan. + * @param[in] x The coordinates where BSplines derivatives are evaluated. + * @param[in] n The number of derivatives to evaluate (in addition to the BSplines values themselves). + */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_basis_and_n_derivs( ddc::DSpan2D derivs, ddc::Coordinate const& x, std::size_t n) const; + /** @brief Compute the integrals of the bsplines + * + * @param[out] int_vals The values of the integrals. It has to be a (1+nbasis) 1D mdspan. + */ template KOKKOS_INLINE_FUNCTION ddc::ChunkSpan integrals( ddc::ChunkSpan int_vals) const; + /** @brief Returns the coordinate of the knot corresponding to the given index for a BSpline. + * + * @param[in] idx Integer identifying index of the knot. + * @return Coordinate of the knot. + */ KOKKOS_INLINE_FUNCTION ddc::Coordinate get_knot(int idx) const noexcept { return ddc::Coordinate(rmin() + idx * ddc::step()); } + /** @brief Returns the first support knot associated to a discrete_element identifying a BSpline. + * + * @param[in] ix Index of the BSpline. + * @return Coordinate of the knot. + */ KOKKOS_INLINE_FUNCTION double get_first_support_knot(discrete_element_type const& ix) const { return get_knot(ix.uid() - degree()); } + /** @brief Returns the last support knot associated to a discrete_element identifying a BSpline. + * + * @param[in] ix Index of the BSpline. + * @return Coordinate of the knot. + */ KOKKOS_INLINE_FUNCTION double get_last_support_knot(discrete_element_type const& ix) const { return get_knot(ix.uid() + 1); } + /** @brief Returns the n-th knot associated to a discrete_element identifying a BSpline. + * + * @param[in] ix Index of the BSpline. + * @param[in] n Integer identifying a knot in the support of the BSpline. + */ KOKKOS_INLINE_FUNCTION double get_support_knot_n(discrete_element_type const& ix, int n) const { return get_knot(ix.uid() + n - degree()); } + /** @brief Returns the coordinate of the lower boundary BSpline. + * + * @return Coordinate of the lower boundary BSpline. + */ KOKKOS_INLINE_FUNCTION ddc::Coordinate rmin() const noexcept { return ddc::coordinate(m_domain.front()); } + /** @brief Returns the coordinate of the upper boundary BSpline. + * + * @return Coordinate of the upper boundary BSpline. + */ KOKKOS_INLINE_FUNCTION ddc::Coordinate rmax() const noexcept { return ddc::coordinate(m_domain.back()); } + /** @brief TODO + * + * @return TODO. + */ KOKKOS_INLINE_FUNCTION double length() const noexcept { return rmax() - rmin(); } + /** @brief TODO + * + * @return TODO. + */ KOKKOS_INLINE_FUNCTION std::size_t size() const noexcept { return degree() + ncells(); } - /// Returns the discrete domain including ghost bsplines + /** @brief Returns the discrete domain including ghost bsplines + * + * @return The discrete domain including ghost bsplines. + */ KOKKOS_INLINE_FUNCTION discrete_domain_type full_domain() const { return discrete_domain_type(discrete_element_type(0), discrete_vector_type(size())); } + /** @brief TODO + * + * @return TODO + */ KOKKOS_INLINE_FUNCTION std::size_t nbasis() const noexcept { return ncells() + !is_periodic() * degree(); } + /** @brief TODO + * + * @return TODO + */ KOKKOS_INLINE_FUNCTION std::size_t ncells() const noexcept { return m_domain.size() - 1; @@ -215,6 +307,11 @@ struct is_uniform_bsplines : public std::is_base_of { }; +/** + * @brief Indicates if a dimension representing BSplines corresponds to uniform BSplines of not. + * + * @tparam The discrete dimension associated to BSplines + */ template constexpr bool is_uniform_bsplines_v = is_uniform_bsplines::value; diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index 7c1824d69..e30e87b23 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -10,24 +10,10 @@ #include "deriv.hpp" namespace ddc { +enum class SplineSolver { + GINKGO +}; // Only GINKGO available atm, other solvers will be implemented in the futur -/** - * @brief An enum determining the backend solver of a SplineBuilder or SplineBuilder2d. - * - * An enum determining the backend solver of a SplineBuilder or SplineBuilder2d. Only GINKGO available at the moment, - * other solvers will be implemented in the futur. - */ -enum class SplineSolver { GINKGO }; - -/** - * @brief An helper giving the uniform/non_uniform status of a spline interpolation mesh according to its attributes. - * - * An helper giving the uniform/non_uniform status of a spline interpolation mesh according to its attributes. - * @param is_uniform A boolean giving the presumed status before considering boundary conditions. - * @param BcXmin The lower boundary condition. - * @param BcXmax The upper boundary condition. - * @param int The degree of the spline. - */ constexpr bool is_spline_interpolation_mesh_uniform( bool const is_uniform, ddc::BoundCond const BcXmin, @@ -48,14 +34,6 @@ constexpr bool is_spline_interpolation_mesh_uniform( * of BSplines. The spline is constructed such that it respects the boundary conditions * BcXmin and BcXmax, and it interpolates the function at the points on the interpolation_mesh * associated with interpolation_mesh_type. - * @tparam ExecSpace The Kokkos execution space on which the spline transform is performed. - * @tparam MemorySpace The Kokkos memory space on which the data (interpolation function and splines coefficients) are stored. - * @tparam BSplines The discrete dimension representing the BSplines. - * @tparam InterpolationMesh The discrete dimension supporting the interpolation points. - * @tparam BcXmin The lower boundary condition. - * @tparam BcXmax The upper boundary condition. - * @tparam Solver The SplineSolver giving the backend used to perform the spline transform. - * @tparam IDimX A variadic template of all the discrete dimensions forming the full space (InterpolationMesh + batched dimensions). */ template < class ExecSpace, @@ -79,79 +57,52 @@ class SplineBuilder using tag_type = typename InterpolationMesh::continuous_dimension_type; public: - /** - * @brief The type of the Kokkos execution space used by this class. - */ using exec_space = ExecSpace; - /** - * @brief The type of the Kokkos memory space used by this class. - */ using memory_space = MemorySpace; /** - * @brief The type of the interpolation discrete dimension (discrete dimension of interest) used by this class. + * @brief The type of the interpolation mesh used by this class. */ using interpolation_mesh_type = InterpolationMesh; /** - * @brief The discrete dimension representing the BSplines. + * @brief The type of the BSplines which are compatible with this class. */ using bsplines_type = BSplines; - /** - * @brief The Deriv dimension at the boundaries. - */ using deriv_type = ddc::Deriv; /** - * @brief The type of the domain for the 1D interpolation mesh used by this class. + * @brief The type of the domain for the interpolation mesh used by this class. */ using interpolation_domain_type = ddc::DiscreteDomain; - /** - * @brief The type of the whole domain representing interpolation points. - */ - using batched_interpolation_domain_type = ddc::DiscreteDomain; + using vals_domain_type = ddc::DiscreteDomain; - /** - * @brief The type of the batch domain (obtained by removing dimension of interest from whole space). - */ using batch_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq>>; - /** - * @brief Helper to get the dimension of batched_spline_domain_type associated to a dimension of batched_interpolation_domain_type. - */ template using spline_dim_type = std::conditional_t, bsplines_type, Tag>; - /** - * @brief The type of the whole spline domain (cartesian product of 1D spline domain and batch domain) preserving the underlying memory layout (order of dimensions). - */ - using batched_spline_domain_type = + using spline_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq, ddc::detail::TypeSeq>>; - /** - * @brief The type of the whole spline domain (cartesian product of 1D spline domain and batch domain) with 1D spline domain being contiguous . - */ - using batched_spline_tr_domain_type = + using spline_tr_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, ddc::type_seq_remove_t< ddc::detail::TypeSeq, ddc::detail::TypeSeq>>>; - /** - * @brief The type of the whole Derivs domain (cartesian product of 1D Deriv domain and batch domain) preserving the underlying memory layout (order of dimensions). - */ - using batched_derivs_domain_type = + using derivs_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq, @@ -163,12 +114,12 @@ class SplineBuilder static constexpr bool s_odd = BSplines::degree() % 2; /** - * @brief The number of equations defining the boundary conditions at the lower bound. + * @brief The number of equations which define the boundary conditions at the lower bound. */ static constexpr int s_nbe_xmin = n_boundary_equations(BcXmin, BSplines::degree()); /** - * @brief The number of equations defining the boundary conditions at the upper bound. + * @brief The number of equations which define the boundary conditions at the upper bound. */ static constexpr int s_nbe_xmax = n_boundary_equations(BcXmax, BSplines::degree()); @@ -201,7 +152,7 @@ class SplineBuilder static constexpr ddc::BoundCond s_bc_xmax = BcXmax; private: - batched_interpolation_domain_type m_batched_interpolation_domain; + vals_domain_type m_vals_domain; int m_offset; @@ -211,22 +162,13 @@ class SplineBuilder std::unique_ptr matrix; public: - /** - * @brief An helper to compute the offset. - */ int compute_offset(interpolation_domain_type const& interpolation_domain); - /** - * @brief Build a SplineBuilder acting on batched_interpolation_domain. - * - * @param batched_interpolation_domain The domain on which are defined the interpolation points. - * @param cols_per_chunk An hyperparameter used by the slicer (internal to the solver) to define the size of a chunk of right-and-sides of the linear problem to be computed in parallel. - */ explicit SplineBuilder( - batched_interpolation_domain_type const& batched_interpolation_domain, + vals_domain_type const& vals_domain, std::optional cols_per_chunk = std::nullopt, std::optional preconditionner_max_block_size = std::nullopt) - : m_batched_interpolation_domain(batched_interpolation_domain) + : m_vals_domain(vals_domain) , m_offset(compute_offset(interpolation_domain())) , m_dx((ddc::discrete_space().rmax() - ddc::discrete_space().rmin()) / ddc::discrete_space().ncells()) @@ -249,123 +191,88 @@ class SplineBuilder preconditionner_max_block_size); } - /// @brief Copy-constructor is deleted SplineBuilder(SplineBuilder const& x) = delete; - /// @brief Move-constructs + /** + * @brief Create a new SplineBuilder by copy + * + * @param x The SplineBuilder being copied. + */ SplineBuilder(SplineBuilder&& x) = default; - /// @brief Destructs ~SplineBuilder() = default; - /// @brief Copy-assignment is deleted SplineBuilder& operator=(SplineBuilder const& x) = delete; - /// @brief Move-assigns - SplineBuilder& operator=(SplineBuilder&& x) = default; - /** - * @brief Get the domain for the 1D interpolation mesh used by this class. + * @brief Copy a SplineBuilder. * - * Get the 1D interpolation domain associated to dimension of interest. - * - * @return The 1D domain for the grid points. + * @param x The SplineBuilder being copied. + * @returns A reference to this object. */ - interpolation_domain_type interpolation_domain() const noexcept + SplineBuilder& operator=(SplineBuilder&& x) = default; + + vals_domain_type vals_domain() const noexcept { - return interpolation_domain_type(m_batched_interpolation_domain); + return m_vals_domain; } /** - * @brief Get the whole domain representing interpolation points. + * @brief Get the domain from which the approximation is defined. * * Get the domain on which values of the function must be provided in order - * to build a spline transform of the function. + * to build a spline approximation of the function. * * @return The domain for the grid points. */ - batched_interpolation_domain_type batched_interpolation_domain() const noexcept + interpolation_domain_type interpolation_domain() const noexcept { - return m_batched_interpolation_domain; + return interpolation_domain_type(vals_domain()); } - /** - * @brief Get the batch domain. - * - * Get the batch domain (obtained by removing dimension of interest from whole interpolation domain). - * - * @return The batch domain. - */ batch_domain_type batch_domain() const noexcept { - return ddc::remove_dims_of(batched_interpolation_domain(), interpolation_domain()); + return ddc::remove_dims_of(vals_domain(), interpolation_domain()); } - /** - * @brief Get the 1D domain on which spline coefficients are defined. - * - * Get the 1D spline domain corresponding to dimension of interest. - * - * @return The 1D domain for the spline coefficients. - */ - ddc::DiscreteDomain spline_domain() const noexcept + ddc::DiscreteDomain bsplines_domain() const noexcept // TODO : clarify name { return ddc::discrete_space().full_domain(); } /** - * @brief Get the whole domain on which spline coefficients are defined, preserving memory layout. + * @brief Get the domain on which the approximation is defined. * - * Get the whole domain on which spline coefficients will be computed, preserving memory layout (order of dimensions). + * Get the domain of the basis-splines for which the coefficients of the spline + * approximation must be calculated. * - * @return The domain for the spline coefficients. + * @return The domain for the splines. */ - batched_spline_domain_type batched_spline_domain() const noexcept + spline_domain_type spline_domain() const noexcept { return ddc::replace_dim_of< interpolation_mesh_type, - bsplines_type>(batched_interpolation_domain(), spline_domain()); + bsplines_type>(vals_domain(), bsplines_domain()); } - /** - * @brief Get the whole domain on which spline coefficients are defined, with dimension of interest contiguous. - * - * Get the (transposed) whole domain on which spline coefficients will be computed, with dimension of interest contiguous. - * - * @return The (transposed) domain for the spline coefficients. - */ - batched_spline_tr_domain_type batched_spline_tr_domain() const noexcept + spline_tr_domain_type spline_tr_domain() const noexcept { - return batched_spline_tr_domain_type(spline_domain(), batch_domain()); + return spline_tr_domain_type(bsplines_domain(), batch_domain()); } - /** - * @brief Get the whole domain on which derivatives on lower boundary are defined. - * - * Get the whole domain on which derivatives on lower boundary are defined. This is used only with HERMITE boundary conditions. - * - * @return The domain for the Derivs values. - */ - batched_derivs_domain_type batched_derivs_xmin_domain() const noexcept + derivs_domain_type derivs_xmin_domain() const noexcept { return ddc::replace_dim_of( - batched_interpolation_domain(), + vals_domain(), ddc::DiscreteDomain( ddc::DiscreteElement(1), ddc::DiscreteVector(s_nbc_xmin))); } - /** - * @brief Get the whole domain on which derivatives on upper boundary are defined. - * - * Get the whole domain on which derivatives on upper boundary are defined. This is used only with HERMITE boundary conditions. - * - * @return The domain for the Derivs values. - */ - batched_derivs_domain_type batched_derivs_xmax_domain() const noexcept + derivs_domain_type derivs_xmax_domain() const noexcept { return ddc::replace_dim_of( - batched_interpolation_domain(), + vals_domain(), ddc::DiscreteDomain( ddc::DiscreteElement(1), ddc::DiscreteVector(s_nbc_xmax))); @@ -376,10 +283,6 @@ class SplineBuilder * * Get the interpolation matrix. This can be useful for debugging (as it allows * one to print the matrix) or for more complex quadrature schemes. - * - * Warning: the returned ddc::detail::Matrix class is not supposed to be exposed - * to user, which means its usage is not tested out of the scope of DDC splines transforms. - * Use at your own risk. * * @return A reference to the interpolation matrix. */ @@ -401,27 +304,20 @@ class SplineBuilder * * @param[out] spline The coefficients of the spline calculated by the function. * @param[in] vals The values of the function at the grid points. - * @param[in] derivs_xmin The values of the derivatives at the lower boundary - * (used only with HERMITE lower boundary condition). - * @param[in] derivs_xmax The values of the derivatives at the upper boundary - * (used only with HERMITE upper boundary condition). + * @param[in] derivs_xmin The values of the derivatives at the lower boundary. + * @param[in] derivs_xmax The values of the derivatives at the upper boundary. */ template void operator()( - ddc::ChunkSpan spline, - ddc::ChunkSpan - vals, - std::optional> const derivs_xmin + ddc::ChunkSpan spline, + ddc::ChunkSpan vals, + std::optional< + ddc::ChunkSpan> const + derivs_xmin = std::nullopt, - std::optional> const derivs_xmax + std::optional< + ddc::ChunkSpan> const + derivs_xmax = std::nullopt) const; private: @@ -742,18 +638,12 @@ void SplineBuilder< Solver, IDimX...>:: operator()( - ddc::ChunkSpan spline, - ddc::ChunkSpan vals, - std::optional> const derivs_xmin, - std::optional> const derivs_xmax) const + ddc::ChunkSpan spline, + ddc::ChunkSpan vals, + std::optional> const + derivs_xmin, + std::optional> const + derivs_xmax) const { assert(vals.template extent() == ddc::discrete_space().nbasis() - s_nbe_xmin - s_nbe_xmax); @@ -828,9 +718,7 @@ operator()( // TODO : Consider optimizing // Allocate and fill a transposed version of spline in order to get dimension of interest as last dimension (optimal for GPU, necessary for Ginkgo) - ddc::Chunk spline_tr_alloc( - batched_spline_tr_domain(), - ddc::KokkosAllocator()); + ddc::Chunk spline_tr_alloc(spline_tr_domain(), ddc::KokkosAllocator()); ddc::ChunkSpan spline_tr = spline_tr_alloc.span_view(); ddc::parallel_for_each( exec_space(), diff --git a/include/ddc/kernels/splines/spline_builder_2d.hpp b/include/ddc/kernels/splines/spline_builder_2d.hpp index 872bf2956..372954e96 100644 --- a/include/ddc/kernels/splines/spline_builder_2d.hpp +++ b/include/ddc/kernels/splines/spline_builder_2d.hpp @@ -87,14 +87,7 @@ class SplineBuilder2D */ using bsplines_type2 = typename builder_type2::bsplines_type; - /** - * @brief The type of the Deriv domain on boundaries in the first dimension which are compatible with this class. - */ using deriv_type1 = typename builder_type1::deriv_type; - - /** - * @brief The type of the Deriv domain on boundaries in the second dimension which are compatible with this class. - */ using deriv_type2 = typename builder_type2::deriv_type; /** @@ -120,26 +113,26 @@ class SplineBuilder2D using interpolation_domain_type = ddc::DiscreteDomain; - using batched_interpolation_domain_type = ddc::DiscreteDomain; + using vals_domain_type = ddc::DiscreteDomain; using batch_domain_type = ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq>>; - using batched_spline_domain_type + using spline_domain_type = ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq, ddc::detail::TypeSeq>>; - using batched_derivs_domain_type1 = typename builder_type1::batched_derivs_domain_type; - using batched_derivs_domain_type2 + using derivs_domain_type1 = typename builder_type1::derivs_domain_type; + using derivs_domain_type2 = ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq, ddc::detail::TypeSeq>>; - using batched_derivs_domain_type + using derivs_domain_type = ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq, @@ -154,27 +147,24 @@ class SplineBuilder2D /** * @brief Create a new SplineBuilder2D. * - * @param batched_interpolation_domain + * @param vals_domain * The 2D domain on which points will be provided in order to * create the 2D spline approximation. * @param cols_per_chunk The number of columns in the rhs passed to the underlying linear solver. * @param preconditionner_max_block_size The block size of in the block Jacobi preconditioner. */ explicit SplineBuilder2D( - batched_interpolation_domain_type const& batched_interpolation_domain, + vals_domain_type const& vals_domain, std::optional cols_per_chunk = std::nullopt, std::optional preconditionner_max_block_size = std::nullopt) - : m_spline_builder1( - batched_interpolation_domain, - cols_per_chunk, - preconditionner_max_block_size) + : m_spline_builder1(vals_domain, cols_per_chunk, preconditionner_max_block_size) , m_spline_builder_deriv1(ddc::replace_dim_of( - m_spline_builder1.batched_interpolation_domain(), + m_spline_builder1.vals_domain(), ddc::DiscreteDomain( ddc::DiscreteElement(1), ddc::DiscreteVector(bsplines_type2::degree() / 2)))) , m_spline_builder2( - m_spline_builder1.batched_spline_domain(), + m_spline_builder1.spline_domain(), cols_per_chunk, preconditionner_max_block_size) { @@ -210,9 +200,9 @@ class SplineBuilder2D */ SplineBuilder2D& operator=(SplineBuilder2D&& x) = default; - batched_interpolation_domain_type batched_interpolation_domain() const noexcept + vals_domain_type vals_domain() const noexcept { - return m_spline_builder1.batched_interpolation_domain(); + return m_spline_builder1.vals_domain(); } /** @@ -232,7 +222,7 @@ class SplineBuilder2D batch_domain_type batch_domain() const noexcept { - return ddc::remove_dims_of(batched_interpolation_domain(), interpolation_domain()); + return ddc::remove_dims_of(vals_domain(), interpolation_domain()); } /** @@ -243,7 +233,7 @@ class SplineBuilder2D * * @return The 2D domain for the splines. */ - ddc::DiscreteDomain spline_domain() + ddc::DiscreteDomain bsplines_domain() const noexcept // TODO : clarify name { return ddc::DiscreteDomain( @@ -251,13 +241,13 @@ class SplineBuilder2D ddc::discrete_space().full_domain()); } - batched_spline_domain_type batched_spline_domain() const noexcept + spline_domain_type spline_domain() const noexcept { return ddc::replace_dim_of( ddc::replace_dim_of< interpolation_mesh_type2, - bsplines_type2>(batched_interpolation_domain(), spline_domain()), - spline_domain()); + bsplines_type2>(vals_domain(), bsplines_domain()), + bsplines_domain()); } /** @@ -298,56 +288,39 @@ class SplineBuilder2D */ template void operator()( - ddc::ChunkSpan spline, - ddc::ChunkSpan - vals, - std::optional> const derivs_min1 + ddc::ChunkSpan spline, + ddc::ChunkSpan vals, + std::optional< + ddc::ChunkSpan> const + derivs_min1 = std::nullopt, - std::optional> const derivs_max1 + std::optional< + ddc::ChunkSpan> const + derivs_max1 = std::nullopt, - std::optional> const derivs_min2 + std::optional< + ddc::ChunkSpan> const + derivs_min2 = std::nullopt, - std::optional> const derivs_max2 + std::optional< + ddc::ChunkSpan> const + derivs_max2 = std::nullopt, - std::optional> const mixed_derivs_min1_min2 + std::optional< + ddc::ChunkSpan> const + mixed_derivs_min1_min2 = std::nullopt, - std::optional> const mixed_derivs_max1_min2 + std::optional< + ddc::ChunkSpan> const + mixed_derivs_max1_min2 = std::nullopt, - std::optional> const mixed_derivs_min1_max2 + std::optional< + ddc::ChunkSpan> const + mixed_derivs_min1_max2 = std::nullopt, - std::optional> const mixed_derivs_max1_max2 + std::optional< + ddc::ChunkSpan> const + mixed_derivs_max1_max2 = std::nullopt) const; }; @@ -380,53 +353,29 @@ void SplineBuilder2D< Solver, IDimX...>:: operator()( - ddc::ChunkSpan spline, - ddc::ChunkSpan vals, - std::optional> const derivs_min1, - std::optional> const derivs_max1, - std::optional> const derivs_min2, - std::optional> const derivs_max2, - std::optional> const mixed_derivs_min1_min2, - std::optional> const mixed_derivs_max1_min2, - std::optional> const mixed_derivs_min1_max2, - std::optional> const mixed_derivs_max1_max2) const + ddc::ChunkSpan spline, + ddc::ChunkSpan vals, + std::optional> const + derivs_min1, + std::optional> const + derivs_max1, + std::optional> const + derivs_min2, + std::optional> const + derivs_max2, + std::optional> const + mixed_derivs_min1_min2, + std::optional> const + mixed_derivs_max1_min2, + std::optional> const + mixed_derivs_min1_max2, + std::optional> const + mixed_derivs_max1_max2) const { // TODO: perform computations along dimension 1 on different streams ? // Spline1-transform derivs_min2 (to spline1_deriv_min) ddc::Chunk spline1_deriv_min_alloc( - m_spline_builder_deriv1.batched_spline_domain(), + m_spline_builder_deriv1.spline_domain(), ddc::KokkosAllocator()); auto spline1_deriv_min = spline1_deriv_min_alloc.span_view(); auto spline1_deriv_min_opt = std::optional(spline1_deriv_min.span_cview()); @@ -442,7 +391,7 @@ operator()( // Spline1-transform vals (to spline1) ddc::Chunk spline1_alloc( - m_spline_builder1.batched_spline_domain(), + m_spline_builder1.spline_domain(), ddc::KokkosAllocator()); ddc::ChunkSpan spline1 = spline1_alloc.span_view(); @@ -450,7 +399,7 @@ operator()( // Spline1-transform derivs_max2 (to spline1_deriv_max) ddc::Chunk spline1_deriv_max_alloc( - m_spline_builder_deriv1.batched_spline_domain(), + m_spline_builder_deriv1.spline_domain(), ddc::KokkosAllocator()); auto spline1_deriv_max = spline1_deriv_max_alloc.span_view(); auto spline1_deriv_max_opt = std::optional(spline1_deriv_max.span_cview()); From 56dbf4e0986a108b8558952b7b58b127471ceeec Mon Sep 17 00:00:00 2001 From: blegouix Date: Thu, 18 Apr 2024 14:53:06 +0200 Subject: [PATCH 021/189] remove bsplines (not in the scope of this MR anymore) --- .../kernels/splines/bsplines_non_uniform.hpp | 102 +--------------- .../ddc/kernels/splines/bsplines_uniform.hpp | 115 ++---------------- 2 files changed, 13 insertions(+), 204 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index 20e6ca2d7..0715564d7 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -24,55 +24,44 @@ struct NonUniformBSplinesBase { }; -/** - * The type of a non-uniform BSplines 1D basis. - * - * @tparam Tag The tag identifying the continuous dimension which supports the building of the BSplines. - * @tparam D The degree of the BSplines. - */ +/// NonUniformPointSampling specialization of BSplines template class NonUniformBSplines : NonUniformBSplinesBase { static_assert(D > 0, "Parameter `D` must be positive"); public: - /// @brief The tag identifying the continuous dimension which supports the building of the BSplines. using tag_type = Tag; - /// @brief The discrete dimension corresponding to BSplines. + using discrete_dimension_type = NonUniformBSplines; - /// @brief The rank. +public: static constexpr std::size_t rank() { return 1; } - /// @brief The degree of BSplines. static constexpr std::size_t degree() noexcept { return D; } - /// @brief Indicates if the BSplines are periodic or not. static constexpr bool is_periodic() noexcept { return Tag::PERIODIC; } - /// @brief Indicates if the BSplines are radial or not (should be deprecated soon because this concept is not in the scope of DDC). static constexpr bool is_radial() noexcept { return false; } - /// @brief Indicates if the BSplines are uniform or not (this is obviously the case here). static constexpr bool is_uniform() noexcept { return false; } - /// @brief Impl template class Impl { @@ -87,16 +76,12 @@ class NonUniformBSplines : NonUniformBSplinesBase int m_nknots; public: - /// @brief The type of discrete dimension associated to BSplines. using discrete_dimension_type = NonUniformBSplines; - /// @brief The type of discrete domain indexing the BSplines. using discrete_domain_type = DiscreteDomain; - /// @brief The type of discrete element indexing a BSpline. using discrete_element_type = DiscreteElement; - /// @brief The type of discrete vector representing an "indexes displacement" between two BSplines. using discrete_vector_type = DiscreteVector; Impl() = default; @@ -124,97 +109,49 @@ class NonUniformBSplines : NonUniformBSplinesBase template Impl(RandomIt breaks_begin, RandomIt breaks_end); - /// @brief Copy-constructs Impl(Impl const& x) = default; - /// @brief Move-constructs Impl(Impl&& x) = default; - /// @brief Destructs ~Impl() = default; - /// @brief Copy-assigns Impl& operator=(Impl const& x) = default; - /// @brief Move-assigns Impl& operator=(Impl&& x) = default; - /** @brief Evaluates BSplines at a given coordinate - * - * The values are computed for every BSplines at the given coordinate x. A spline approximation at coordinate x is a linear combination of those BSplines evaluations weigthed with splines coefficients of the spline-transformed initial discrete function. - * @param[out] values The values of the BSplines evaluated at coordinate x. It has to be a (1+degree) 1D mdspan. - * @param[in] x The coordinates where BSplines are evaluated. - */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_basis(DSpan1D values, ddc::Coordinate const& x) const; - /** @brief Evaluates BSplines derivatives at a given coordinate - * - * The derivatives are computed for every BSplines at the given coordinate x. A spline approximation of a derivative at coordinate x is a linear combination of those BSplines derivatives weigthed with splines coefficients of the spline-transformed initial discrete function. - * @param[out] derivs The derivatives of the BSplines evaluated at coordinate x. It has to be a (1+degree) 1D mdspan. - * @param[in] x The coordinates where BSplines derivatives are evaluated. - */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_deriv(DSpan1D derivs, ddc::Coordinate const& x) const; - /** @brief Evaluates BSplines values and n derivatives at a given coordinate - * - * The values and derivatives are computed for every BSplines at the given coordinate x. - * @param[out] derivs The values and n derivatives of the BSplines evaluated at coordinate x. It has to be a (1+degree)*(1+n) 2D mdspan. - * @param[in] x The coordinates where BSplines derivatives are evaluated. - * @param[in] n The number of derivatives to evaluate (in addition to the BSplines values themselves). - */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_basis_and_n_derivs( ddc::DSpan2D derivs, ddc::Coordinate const& x, std::size_t n) const; - /** @brief Compute the integrals of the bsplines - * - * @param[out] int_vals The values of the integrals. It has to be a (1+nbasis) 1D mdspan. - */ template KOKKOS_INLINE_FUNCTION ddc::ChunkSpan integrals( ddc::ChunkSpan int_vals) const; - /** @brief Returns the coordinate of the knot corresponding to the given index for a BSpline. - * - * @param[in] idx Integer identifying index of the knot. - * @return Coordinate of the knot. - */ KOKKOS_INLINE_FUNCTION ddc::Coordinate get_knot(int knot_idx) const noexcept { return ddc::coordinate(ddc::DiscreteElement(knot_idx + degree())); } - /** @brief Returns the first support knot associated to a discrete_element identifying a BSpline. - * - * @param[in] ix Index of the BSpline. - * @return Coordinate of the knot. - */ KOKKOS_INLINE_FUNCTION ddc::Coordinate get_first_support_knot( discrete_element_type const& ix) const { return ddc::coordinate(ddc::DiscreteElement(ix.uid())); } - /** @brief Returns the last support knot associated to a discrete_element identifying a BSpline. - * - * @param[in] ix Index of the BSpline. - * @return Coordinate of the knot. - */ KOKKOS_INLINE_FUNCTION ddc::Coordinate get_last_support_knot( discrete_element_type const& ix) const { return ddc::coordinate(ddc::DiscreteElement(ix.uid() + degree() + 1)); } - /** @brief Returns the n-th knot associated to a discrete_element identifying a BSpline. - * - * @param[in] ix Index of the BSpline. - * @param[in] n Integer identifying a knot in the support of the BSpline. - */ KOKKOS_INLINE_FUNCTION ddc::Coordinate get_support_knot_n( discrete_element_type const& ix, int n) const @@ -222,73 +159,42 @@ class NonUniformBSplines : NonUniformBSplinesBase return ddc::coordinate(ddc::DiscreteElement(ix.uid() + n)); } - /** @brief Returns the coordinate of the lower boundary BSpline. - * - * @return Coordinate of the lower boundary BSpline. - */ KOKKOS_INLINE_FUNCTION ddc::Coordinate rmin() const noexcept { return get_knot(0); } - /** @brief Returns the coordinate of the upper boundary BSpline. - * - * @return Coordinate of the upper boundary BSpline. - */ KOKKOS_INLINE_FUNCTION ddc::Coordinate rmax() const noexcept { return get_knot(ncells()); } - /** @brief TODO - * - * @return TODO. - */ KOKKOS_INLINE_FUNCTION double length() const noexcept { return rmax() - rmin(); } - /** @brief TODO - * - * @return TODO. - */ KOKKOS_INLINE_FUNCTION std::size_t size() const noexcept { return degree() + ncells(); } - /** @brief Returns the discrete domain including ghost bsplines - * - * @return The discrete domain including ghost bsplines. - */ + /// Returns the discrete domain including ghost bsplines KOKKOS_INLINE_FUNCTION discrete_domain_type full_domain() const { return discrete_domain_type(discrete_element_type(0), discrete_vector_type(size())); } - /** @brief TODO - * - * @return TODO - */ KOKKOS_INLINE_FUNCTION std::size_t npoints() const noexcept { return m_nknots - 2 * degree(); } - /** @brief TODO - * - * @return TODO - */ KOKKOS_INLINE_FUNCTION std::size_t nbasis() const noexcept { return ncells() + !is_periodic() * degree(); } - /** @brief TODO - * - * @return TODO - */ KOKKOS_INLINE_FUNCTION std::size_t ncells() const noexcept { return npoints() - 1; diff --git a/include/ddc/kernels/splines/bsplines_uniform.hpp b/include/ddc/kernels/splines/bsplines_uniform.hpp index e12adf956..c654e482a 100644 --- a/include/ddc/kernels/splines/bsplines_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_uniform.hpp @@ -24,55 +24,43 @@ struct UniformBSplinesBase { }; -/** - * The type of a uniform BSplines 1D basis. - * - * @tparam Tag The tag identifying the continuous dimension which supports the building of the BSplines. - * @tparam D The degree of the BSplines. - */ template class UniformBSplines : UniformBSplinesBase { static_assert(D > 0, "Parameter `D` must be positive"); public: - /// @brief The tag identifying the continuous dimension which supports the building of the BSplines. using tag_type = Tag; - /// @brief The discrete dimension corresponding to BSplines. + using discrete_dimension_type = UniformBSplines; - /// @brief The rank. +public: static constexpr std::size_t rank() { return 1; } - /// @brief The degree of BSplines. static constexpr std::size_t degree() noexcept { return D; } - /// @brief Indicates if the BSplines are periodic or not. static constexpr bool is_periodic() noexcept { return Tag::PERIODIC; } - /// @brief Indicates if the BSplines are radial or not (should be deprecated soon because this concept is not in the scope of DDC). static constexpr bool is_radial() noexcept { return false; } - /// @brief Indicates if the BSplines are uniform or not (this is obviously the case here). static constexpr bool is_uniform() noexcept { return true; } - /// @brief Impl template class Impl { @@ -86,19 +74,20 @@ class UniformBSplines : UniformBSplinesBase ddc::DiscreteDomain m_domain; public: - /// @brief The type of discrete dimension associated to BSplines. using discrete_dimension_type = UniformBSplines; - /// @brief The type of discrete domain indexing the BSplines. using discrete_domain_type = DiscreteDomain; - /// @brief The type of discrete element indexing a BSpline. using discrete_element_type = DiscreteElement; - /// @brief The type of discrete vector representing an "indexes displacement" between two BSplines. using discrete_vector_type = DiscreteVector; - Impl() = default; + Impl() = default; + + template + explicit Impl(Impl const& impl) : m_domain(impl.m_domain) + { + } /** Constructs a BSpline basis with n equidistant knots over \f$[a, b]\f$ * @@ -118,33 +107,16 @@ class UniformBSplines : UniformBSplinesBase mesh_type>(rmin, rmax, ddc::DiscreteVector(ncells + 1))); } - /// @brief Copy-constructs from another impl with different Kokkos memory space - template - explicit Impl(Impl const& impl) : m_domain(impl.m_domain) - { - } - - /// @brief Copy-constructs Impl(Impl const& x) = default; - /// @brief Move-constructs Impl(Impl&& x) = default; - /// @brief Destructs ~Impl() = default; - /// @brief Copy-assigns Impl& operator=(Impl const& x) = default; - /// @brief Move-assigns Impl& operator=(Impl&& x) = default; - /** @brief Evaluates BSplines at a given coordinate - * - * The values are computed for every BSplines at the given coordinate x. A spline approximation at coordinate x is a linear combination of those BSplines evaluations weigthed with splines coefficients of the spline-transformed initial discrete function. - * @param[out] values The values of the BSplines evaluated at coordinate x. It has to be a (1+degree) 1D mdspan. - * @param[in] x The coordinates where BSplines are evaluated. - */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_basis(DSpan1D values, ddc::Coordinate const& x) const { @@ -152,135 +124,71 @@ class UniformBSplines : UniformBSplinesBase return eval_basis(values, x, degree()); } - /** @brief Evaluates BSplines derivatives at a given coordinate - * - * The derivatives are computed for every BSplines at the given coordinate x. A spline approximation of a derivative at coordinate x is a linear combination of those BSplines derivatives weigthed with splines coefficients of the spline-transformed initial discrete function. - * @param[out] derivs The derivatives of the BSplines evaluated at coordinate x. It has to be a (1+degree) 1D mdspan. - * @param[in] x The coordinates where BSplines derivatives are evaluated. - */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_deriv(DSpan1D derivs, ddc::Coordinate const& x) const; - /** @brief Evaluates BSplines values and n derivatives at a given coordinate - * - * The values and derivatives are computed for every BSplines at the given coordinate x. - * @param[out] derivs The values and n derivatives of the BSplines evaluated at coordinate x. It has to be a (1+degree)*(1+n) 2D mdspan. - * @param[in] x The coordinates where BSplines derivatives are evaluated. - * @param[in] n The number of derivatives to evaluate (in addition to the BSplines values themselves). - */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_basis_and_n_derivs( ddc::DSpan2D derivs, ddc::Coordinate const& x, std::size_t n) const; - /** @brief Compute the integrals of the bsplines - * - * @param[out] int_vals The values of the integrals. It has to be a (1+nbasis) 1D mdspan. - */ template KOKKOS_INLINE_FUNCTION ddc::ChunkSpan integrals( ddc::ChunkSpan int_vals) const; - /** @brief Returns the coordinate of the knot corresponding to the given index for a BSpline. - * - * @param[in] idx Integer identifying index of the knot. - * @return Coordinate of the knot. - */ KOKKOS_INLINE_FUNCTION ddc::Coordinate get_knot(int idx) const noexcept { return ddc::Coordinate(rmin() + idx * ddc::step()); } - /** @brief Returns the first support knot associated to a discrete_element identifying a BSpline. - * - * @param[in] ix Index of the BSpline. - * @return Coordinate of the knot. - */ KOKKOS_INLINE_FUNCTION double get_first_support_knot(discrete_element_type const& ix) const { return get_knot(ix.uid() - degree()); } - /** @brief Returns the last support knot associated to a discrete_element identifying a BSpline. - * - * @param[in] ix Index of the BSpline. - * @return Coordinate of the knot. - */ KOKKOS_INLINE_FUNCTION double get_last_support_knot(discrete_element_type const& ix) const { return get_knot(ix.uid() + 1); } - /** @brief Returns the n-th knot associated to a discrete_element identifying a BSpline. - * - * @param[in] ix Index of the BSpline. - * @param[in] n Integer identifying a knot in the support of the BSpline. - */ KOKKOS_INLINE_FUNCTION double get_support_knot_n(discrete_element_type const& ix, int n) const { return get_knot(ix.uid() + n - degree()); } - /** @brief Returns the coordinate of the lower boundary BSpline. - * - * @return Coordinate of the lower boundary BSpline. - */ KOKKOS_INLINE_FUNCTION ddc::Coordinate rmin() const noexcept { return ddc::coordinate(m_domain.front()); } - /** @brief Returns the coordinate of the upper boundary BSpline. - * - * @return Coordinate of the upper boundary BSpline. - */ KOKKOS_INLINE_FUNCTION ddc::Coordinate rmax() const noexcept { return ddc::coordinate(m_domain.back()); } - /** @brief TODO - * - * @return TODO. - */ KOKKOS_INLINE_FUNCTION double length() const noexcept { return rmax() - rmin(); } - /** @brief TODO - * - * @return TODO. - */ KOKKOS_INLINE_FUNCTION std::size_t size() const noexcept { return degree() + ncells(); } - /** @brief Returns the discrete domain including ghost bsplines - * - * @return The discrete domain including ghost bsplines. - */ + /// Returns the discrete domain including ghost bsplines KOKKOS_INLINE_FUNCTION discrete_domain_type full_domain() const { return discrete_domain_type(discrete_element_type(0), discrete_vector_type(size())); } - /** @brief TODO - * - * @return TODO - */ KOKKOS_INLINE_FUNCTION std::size_t nbasis() const noexcept { return ncells() + !is_periodic() * degree(); } - /** @brief TODO - * - * @return TODO - */ KOKKOS_INLINE_FUNCTION std::size_t ncells() const noexcept { return m_domain.size() - 1; @@ -307,11 +215,6 @@ struct is_uniform_bsplines : public std::is_base_of { }; -/** - * @brief Indicates if a dimension representing BSplines corresponds to uniform BSplines of not. - * - * @tparam The discrete dimension associated to BSplines - */ template constexpr bool is_uniform_bsplines_v = is_uniform_bsplines::value; From 85a2a0fdaaa7b19ff5316091a07426b826e9f4c0 Mon Sep 17 00:00:00 2001 From: blegouix Date: Thu, 18 Apr 2024 15:21:55 +0200 Subject: [PATCH 022/189] format --- .../kernels/splines/bsplines_non_uniform.hpp | 24 ++++++++-------- .../ddc/kernels/splines/bsplines_uniform.hpp | 28 +++++++++---------- 2 files changed, 26 insertions(+), 26 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index 20e6ca2d7..e371f296a 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -36,43 +36,43 @@ class NonUniformBSplines : NonUniformBSplinesBase static_assert(D > 0, "Parameter `D` must be positive"); public: - /// @brief The tag identifying the continuous dimension which supports the building of the BSplines. + /// @brief The tag identifying the continuous dimension which supports the building of the BSplines. using tag_type = Tag; - /// @brief The discrete dimension corresponding to BSplines. + /// @brief The discrete dimension corresponding to BSplines. using discrete_dimension_type = NonUniformBSplines; - /// @brief The rank. + /// @brief The rank. static constexpr std::size_t rank() { return 1; } - /// @brief The degree of BSplines. + /// @brief The degree of BSplines. static constexpr std::size_t degree() noexcept { return D; } - /// @brief Indicates if the BSplines are periodic or not. + /// @brief Indicates if the BSplines are periodic or not. static constexpr bool is_periodic() noexcept { return Tag::PERIODIC; } - /// @brief Indicates if the BSplines are radial or not (should be deprecated soon because this concept is not in the scope of DDC). + /// @brief Indicates if the BSplines are radial or not (should be deprecated soon because this concept is not in the scope of DDC). static constexpr bool is_radial() noexcept { return false; } - /// @brief Indicates if the BSplines are uniform or not (this is obviously the case here). + /// @brief Indicates if the BSplines are uniform or not (this is obviously the case here). static constexpr bool is_uniform() noexcept { return false; } - /// @brief Impl + /// @brief Impl template class Impl { @@ -87,16 +87,16 @@ class NonUniformBSplines : NonUniformBSplinesBase int m_nknots; public: - /// @brief The type of discrete dimension associated to BSplines. + /// @brief The type of discrete dimension associated to BSplines. using discrete_dimension_type = NonUniformBSplines; - /// @brief The type of discrete domain indexing the BSplines. + /// @brief The type of discrete domain indexing the BSplines. using discrete_domain_type = DiscreteDomain; - /// @brief The type of discrete element indexing a BSpline. + /// @brief The type of discrete element indexing a BSpline. using discrete_element_type = DiscreteElement; - /// @brief The type of discrete vector representing an "indexes displacement" between two BSplines. + /// @brief The type of discrete vector representing an "indexes displacement" between two BSplines. using discrete_vector_type = DiscreteVector; Impl() = default; diff --git a/include/ddc/kernels/splines/bsplines_uniform.hpp b/include/ddc/kernels/splines/bsplines_uniform.hpp index e12adf956..afabf9b58 100644 --- a/include/ddc/kernels/splines/bsplines_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_uniform.hpp @@ -36,43 +36,43 @@ class UniformBSplines : UniformBSplinesBase static_assert(D > 0, "Parameter `D` must be positive"); public: - /// @brief The tag identifying the continuous dimension which supports the building of the BSplines. + /// @brief The tag identifying the continuous dimension which supports the building of the BSplines. using tag_type = Tag; - /// @brief The discrete dimension corresponding to BSplines. + /// @brief The discrete dimension corresponding to BSplines. using discrete_dimension_type = UniformBSplines; - /// @brief The rank. + /// @brief The rank. static constexpr std::size_t rank() { return 1; } - /// @brief The degree of BSplines. + /// @brief The degree of BSplines. static constexpr std::size_t degree() noexcept { return D; } - /// @brief Indicates if the BSplines are periodic or not. + /// @brief Indicates if the BSplines are periodic or not. static constexpr bool is_periodic() noexcept { return Tag::PERIODIC; } - /// @brief Indicates if the BSplines are radial or not (should be deprecated soon because this concept is not in the scope of DDC). + /// @brief Indicates if the BSplines are radial or not (should be deprecated soon because this concept is not in the scope of DDC). static constexpr bool is_radial() noexcept { return false; } - /// @brief Indicates if the BSplines are uniform or not (this is obviously the case here). + /// @brief Indicates if the BSplines are uniform or not (this is obviously the case here). static constexpr bool is_uniform() noexcept { return true; } - /// @brief Impl + /// @brief Impl template class Impl { @@ -86,19 +86,19 @@ class UniformBSplines : UniformBSplinesBase ddc::DiscreteDomain m_domain; public: - /// @brief The type of discrete dimension associated to BSplines. + /// @brief The type of discrete dimension associated to BSplines. using discrete_dimension_type = UniformBSplines; - /// @brief The type of discrete domain indexing the BSplines. + /// @brief The type of discrete domain indexing the BSplines. using discrete_domain_type = DiscreteDomain; - /// @brief The type of discrete element indexing a BSpline. + /// @brief The type of discrete element indexing a BSpline. using discrete_element_type = DiscreteElement; - /// @brief The type of discrete vector representing an "indexes displacement" between two BSplines. + /// @brief The type of discrete vector representing an "indexes displacement" between two BSplines. using discrete_vector_type = DiscreteVector; - Impl() = default; + Impl() = default; /** Constructs a BSpline basis with n equidistant knots over \f$[a, b]\f$ * @@ -182,7 +182,7 @@ class UniformBSplines : UniformBSplinesBase integrals( ddc::ChunkSpan int_vals) const; - /** @brief Returns the coordinate of the knot corresponding to the given index for a BSpline. + /** @brief Returns the coordinate of the knot corresponding to the given index for a BSpline. * * @param[in] idx Integer identifying index of the knot. * @return Coordinate of the knot. From 17bb0ba81db4b9ed703793d4fbf9c82fc757f5ab Mon Sep 17 00:00:00 2001 From: blegouix Date: Thu, 18 Apr 2024 19:23:05 +0200 Subject: [PATCH 023/189] autoreview --- .../kernels/splines/bsplines_non_uniform.hpp | 29 ++++++++------- .../ddc/kernels/splines/bsplines_uniform.hpp | 36 +++++++++---------- 2 files changed, 35 insertions(+), 30 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index e371f296a..f2a027642 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -39,7 +39,7 @@ class NonUniformBSplines : NonUniformBSplinesBase /// @brief The tag identifying the continuous dimension which supports the building of the BSplines. using tag_type = Tag; - /// @brief The discrete dimension corresponding to BSplines. + /// @brief The discrete dimension identifying BSplines. using discrete_dimension_type = NonUniformBSplines; /// @brief The rank. @@ -66,7 +66,7 @@ class NonUniformBSplines : NonUniformBSplinesBase return false; } - /// @brief Indicates if the BSplines are uniform or not (this is obviously the case here). + /// @brief Indicates if the BSplines are uniform or not (this is not the case here). static constexpr bool is_uniform() noexcept { return false; @@ -87,7 +87,7 @@ class NonUniformBSplines : NonUniformBSplinesBase int m_nknots; public: - /// @brief The type of discrete dimension associated to BSplines. + /// @brief The type of discrete dimension identifying BSplines. using discrete_dimension_type = NonUniformBSplines; /// @brief The type of discrete domain indexing the BSplines. @@ -143,7 +143,7 @@ class NonUniformBSplines : NonUniformBSplinesBase * * The values are computed for every BSplines at the given coordinate x. A spline approximation at coordinate x is a linear combination of those BSplines evaluations weigthed with splines coefficients of the spline-transformed initial discrete function. * @param[out] values The values of the BSplines evaluated at coordinate x. It has to be a (1+degree) 1D mdspan. - * @param[in] x The coordinates where BSplines are evaluated. + * @param[in] x The coordinate where BSplines are evaluated. */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_basis(DSpan1D values, ddc::Coordinate const& x) const; @@ -152,7 +152,7 @@ class NonUniformBSplines : NonUniformBSplinesBase * * The derivatives are computed for every BSplines at the given coordinate x. A spline approximation of a derivative at coordinate x is a linear combination of those BSplines derivatives weigthed with splines coefficients of the spline-transformed initial discrete function. * @param[out] derivs The derivatives of the BSplines evaluated at coordinate x. It has to be a (1+degree) 1D mdspan. - * @param[in] x The coordinates where BSplines derivatives are evaluated. + * @param[in] x The coordinate where BSplines derivatives are evaluated. */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_deriv(DSpan1D derivs, ddc::Coordinate const& x) const; @@ -169,7 +169,7 @@ class NonUniformBSplines : NonUniformBSplinesBase ddc::Coordinate const& x, std::size_t n) const; - /** @brief Compute the integrals of the bsplines + /** @brief Compute the integrals of the BSplines. * * @param[out] int_vals The values of the integrals. It has to be a (1+nbasis) 1D mdspan. */ @@ -180,7 +180,7 @@ class NonUniformBSplines : NonUniformBSplinesBase /** @brief Returns the coordinate of the knot corresponding to the given index for a BSpline. * - * @param[in] idx Integer identifying index of the knot. + * @param[in] knot_idx Integer identifying index of the knot. * @return Coordinate of the knot. */ KOKKOS_INLINE_FUNCTION ddc::Coordinate get_knot(int knot_idx) const noexcept @@ -190,7 +190,7 @@ class NonUniformBSplines : NonUniformBSplinesBase /** @brief Returns the first support knot associated to a discrete_element identifying a BSpline. * - * @param[in] ix Index of the BSpline. + * @param[in] ix DiscreteElement identifying the BSpline. * @return Coordinate of the knot. */ KOKKOS_INLINE_FUNCTION ddc::Coordinate get_first_support_knot( @@ -201,7 +201,7 @@ class NonUniformBSplines : NonUniformBSplinesBase /** @brief Returns the last support knot associated to a discrete_element identifying a BSpline. * - * @param[in] ix Index of the BSpline. + * @param[in] ix DiscreteElement identifying the BSpline. * @return Coordinate of the knot. */ KOKKOS_INLINE_FUNCTION ddc::Coordinate get_last_support_knot( @@ -210,10 +210,10 @@ class NonUniformBSplines : NonUniformBSplinesBase return ddc::coordinate(ddc::DiscreteElement(ix.uid() + degree() + 1)); } - /** @brief Returns the n-th knot associated to a discrete_element identifying a BSpline. + /** @brief Returns the \f$n\f$-th knot associated to a discrete_element identifying a BSpline. * - * @param[in] ix Index of the BSpline. - * @param[in] n Integer identifying a knot in the support of the BSpline. + * @param[in] ix DiscreteElement identifying the BSpline. + * @param[in] n Integer indexing a knot in the support of the BSpline. */ KOKKOS_INLINE_FUNCTION ddc::Coordinate get_support_knot_n( discrete_element_type const& ix, @@ -304,6 +304,11 @@ struct is_non_uniform_bsplines : public std::is_base_of constexpr bool is_non_uniform_bsplines_v = is_non_uniform_bsplines::value; diff --git a/include/ddc/kernels/splines/bsplines_uniform.hpp b/include/ddc/kernels/splines/bsplines_uniform.hpp index afabf9b58..6e3106610 100644 --- a/include/ddc/kernels/splines/bsplines_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_uniform.hpp @@ -39,7 +39,7 @@ class UniformBSplines : UniformBSplinesBase /// @brief The tag identifying the continuous dimension which supports the building of the BSplines. using tag_type = Tag; - /// @brief The discrete dimension corresponding to BSplines. + /// @brief The discrete dimension representing BSplines. using discrete_dimension_type = UniformBSplines; /// @brief The rank. @@ -66,7 +66,7 @@ class UniformBSplines : UniformBSplinesBase return false; } - /// @brief Indicates if the BSplines are uniform or not (this is obviously the case here). + /// @brief Indicates if the BSplines are uniform or not (this is the case here). static constexpr bool is_uniform() noexcept { return true; @@ -86,7 +86,7 @@ class UniformBSplines : UniformBSplinesBase ddc::DiscreteDomain m_domain; public: - /// @brief The type of discrete dimension associated to BSplines. + /// @brief The type of discrete dimension identifying BSplines. using discrete_dimension_type = UniformBSplines; /// @brief The type of discrete domain indexing the BSplines. @@ -100,7 +100,7 @@ class UniformBSplines : UniformBSplinesBase Impl() = default; - /** Constructs a BSpline basis with n equidistant knots over \f$[a, b]\f$ + /** Constructs a BSplines basis with n equidistant knots over \f$[a, b]\f$ * * @param rmin the real ddc::coordinate of the first knot * @param rmax the real ddc::coordinate of the last knot @@ -118,7 +118,7 @@ class UniformBSplines : UniformBSplinesBase mesh_type>(rmin, rmax, ddc::DiscreteVector(ncells + 1))); } - /// @brief Copy-constructs from another impl with different Kokkos memory space + /// @brief Copy-constructs from another Impl with different Kokkos memory space template explicit Impl(Impl const& impl) : m_domain(impl.m_domain) { @@ -143,7 +143,7 @@ class UniformBSplines : UniformBSplinesBase * * The values are computed for every BSplines at the given coordinate x. A spline approximation at coordinate x is a linear combination of those BSplines evaluations weigthed with splines coefficients of the spline-transformed initial discrete function. * @param[out] values The values of the BSplines evaluated at coordinate x. It has to be a (1+degree) 1D mdspan. - * @param[in] x The coordinates where BSplines are evaluated. + * @param[in] x The coordinate where BSplines are evaluated. */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_basis(DSpan1D values, ddc::Coordinate const& x) const @@ -156,12 +156,12 @@ class UniformBSplines : UniformBSplinesBase * * The derivatives are computed for every BSplines at the given coordinate x. A spline approximation of a derivative at coordinate x is a linear combination of those BSplines derivatives weigthed with splines coefficients of the spline-transformed initial discrete function. * @param[out] derivs The derivatives of the BSplines evaluated at coordinate x. It has to be a (1+degree) 1D mdspan. - * @param[in] x The coordinates where BSplines derivatives are evaluated. + * @param[in] x The coordinate where BSplines derivatives are evaluated. */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_deriv(DSpan1D derivs, ddc::Coordinate const& x) const; - /** @brief Evaluates BSplines values and n derivatives at a given coordinate + /** @brief Evaluates BSplines values and \f$n\f$ derivatives at a given coordinate * * The values and derivatives are computed for every BSplines at the given coordinate x. * @param[out] derivs The values and n derivatives of the BSplines evaluated at coordinate x. It has to be a (1+degree)*(1+n) 2D mdspan. @@ -173,7 +173,7 @@ class UniformBSplines : UniformBSplinesBase ddc::Coordinate const& x, std::size_t n) const; - /** @brief Compute the integrals of the bsplines + /** @brief Compute the integrals of the BSplines. * * @param[out] int_vals The values of the integrals. It has to be a (1+nbasis) 1D mdspan. */ @@ -192,9 +192,9 @@ class UniformBSplines : UniformBSplinesBase return ddc::Coordinate(rmin() + idx * ddc::step()); } - /** @brief Returns the first support knot associated to a discrete_element identifying a BSpline. + /** @brief Returns the first support knot associated to a DiscreteElement identifying a BSpline. * - * @param[in] ix Index of the BSpline. + * @param[in] ix DiscreteElement identifying the BSpline. * @return Coordinate of the knot. */ KOKKOS_INLINE_FUNCTION double get_first_support_knot(discrete_element_type const& ix) const @@ -202,9 +202,9 @@ class UniformBSplines : UniformBSplinesBase return get_knot(ix.uid() - degree()); } - /** @brief Returns the last support knot associated to a discrete_element identifying a BSpline. + /** @brief Returns the last support knot associated to a DiscreteElement identifying a BSpline. * - * @param[in] ix Index of the BSpline. + * @param[in] ix DiscreteElement identifying the BSpline. * @return Coordinate of the knot. */ KOKKOS_INLINE_FUNCTION double get_last_support_knot(discrete_element_type const& ix) const @@ -212,10 +212,10 @@ class UniformBSplines : UniformBSplinesBase return get_knot(ix.uid() + 1); } - /** @brief Returns the n-th knot associated to a discrete_element identifying a BSpline. + /** @brief Returns the \f$n\f$-th knot associated to a discrete_element identifying a BSpline. * - * @param[in] ix Index of the BSpline. - * @param[in] n Integer identifying a knot in the support of the BSpline. + * @param[in] ix DiscreteElement identifying the BSpline. + * @param[in] n Integer indexing a knot in the support of the BSpline. */ KOKKOS_INLINE_FUNCTION double get_support_knot_n(discrete_element_type const& ix, int n) const @@ -308,9 +308,9 @@ struct is_uniform_bsplines : public std::is_base_of }; /** - * @brief Indicates if a dimension representing BSplines corresponds to uniform BSplines of not. + * @brief Indicates if a tag corresponds to uniform BSplines of not. * - * @tparam The discrete dimension associated to BSplines + * @tparam The presumed uniform BSplines. */ template constexpr bool is_uniform_bsplines_v = is_uniform_bsplines::value; From 7e6c05b4e07e9e5329332d2d0362ca272be9a2b8 Mon Sep 17 00:00:00 2001 From: blegouix Date: Thu, 18 Apr 2024 19:57:16 +0200 Subject: [PATCH 024/189] wip --- include/ddc/kernels/splines/bsplines_non_uniform.hpp | 1 + include/ddc/kernels/splines/bsplines_uniform.hpp | 1 + 2 files changed, 2 insertions(+) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index f2a027642..b57173cf7 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -172,6 +172,7 @@ class NonUniformBSplines : NonUniformBSplinesBase /** @brief Compute the integrals of the BSplines. * * @param[out] int_vals The values of the integrals. It has to be a (1+nbasis) 1D mdspan. + * @return The values of the integrals. */ template KOKKOS_INLINE_FUNCTION ddc::ChunkSpan diff --git a/include/ddc/kernels/splines/bsplines_uniform.hpp b/include/ddc/kernels/splines/bsplines_uniform.hpp index 6e3106610..192b30073 100644 --- a/include/ddc/kernels/splines/bsplines_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_uniform.hpp @@ -176,6 +176,7 @@ class UniformBSplines : UniformBSplinesBase /** @brief Compute the integrals of the BSplines. * * @param[out] int_vals The values of the integrals. It has to be a (1+nbasis) 1D mdspan. + * @return The values of the integrals. */ template KOKKOS_INLINE_FUNCTION ddc::ChunkSpan From d7472c7692dfd5f0574e2a1e7672cf83f61740f2 Mon Sep 17 00:00:00 2001 From: blegouix Date: Fri, 19 Apr 2024 08:48:16 +0200 Subject: [PATCH 025/189] wip --- .../kernels/splines/bsplines_non_uniform.hpp | 22 ++++++++++-------- .../ddc/kernels/splines/bsplines_uniform.hpp | 23 +++++++++++-------- 2 files changed, 26 insertions(+), 19 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index fd11570fd..3266b49c9 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -138,6 +138,7 @@ class NonUniformBSplines : NonUniformBSplinesBase * The values are computed for every BSplines at the given coordinate x. A spline approximation at coordinate x is a linear combination of those BSplines evaluations weigthed with splines coefficients of the spline-transformed initial discrete function. * @param[out] values The values of the BSplines evaluated at coordinate x. It has to be a (1+degree) 1D mdspan. * @param[in] x The coordinate where BSplines are evaluated. + * @return TODO */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_basis(DSpan1D values, ddc::Coordinate const& x) const; @@ -147,6 +148,7 @@ class NonUniformBSplines : NonUniformBSplinesBase * The derivatives are computed for every BSplines at the given coordinate x. A spline approximation of a derivative at coordinate x is a linear combination of those BSplines derivatives weigthed with splines coefficients of the spline-transformed initial discrete function. * @param[out] derivs The derivatives of the BSplines evaluated at coordinate x. It has to be a (1+degree) 1D mdspan. * @param[in] x The coordinate where BSplines derivatives are evaluated. + * @return TODO */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_deriv(DSpan1D derivs, ddc::Coordinate const& x) const; @@ -157,6 +159,7 @@ class NonUniformBSplines : NonUniformBSplinesBase * @param[out] derivs The values and n derivatives of the BSplines evaluated at coordinate x. It has to be a (1+degree)*(1+n) 2D mdspan. * @param[in] x The coordinates where BSplines derivatives are evaluated. * @param[in] n The number of derivatives to evaluate (in addition to the BSplines values themselves). + * @return TODO */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_basis_and_n_derivs( ddc::DSpan2D derivs, @@ -183,7 +186,7 @@ class NonUniformBSplines : NonUniformBSplinesBase return ddc::coordinate(ddc::DiscreteElement(knot_idx + degree())); } - /** @brief Returns the first support knot associated to a discrete_element identifying a BSpline. + /** @brief Returns the coordinate of the first support knot associated to a discrete_element identifying a BSpline. * * @param[in] ix DiscreteElement identifying the BSpline. * @return Coordinate of the knot. @@ -194,7 +197,7 @@ class NonUniformBSplines : NonUniformBSplinesBase return ddc::coordinate(ddc::DiscreteElement(ix.uid())); } - /** @brief Returns the last support knot associated to a discrete_element identifying a BSpline. + /** @brief Returns the coordinate of the last support knot associated to a discrete_element identifying a BSpline. * * @param[in] ix DiscreteElement identifying the BSpline. * @return Coordinate of the knot. @@ -205,10 +208,11 @@ class NonUniformBSplines : NonUniformBSplinesBase return ddc::coordinate(ddc::DiscreteElement(ix.uid() + degree() + 1)); } - /** @brief Returns the \f$n\f$-th knot associated to a discrete_element identifying a BSpline. + /** @brief Returns the coordinate of the \f$n\f$-th knot associated to a discrete_element identifying a BSpline. * * @param[in] ix DiscreteElement identifying the BSpline. * @param[in] n Integer indexing a knot in the support of the BSpline. + * @return TODO */ KOKKOS_INLINE_FUNCTION ddc::Coordinate get_support_knot_n( discrete_element_type const& ix, @@ -217,27 +221,27 @@ class NonUniformBSplines : NonUniformBSplinesBase return ddc::coordinate(ddc::DiscreteElement(ix.uid() + n)); } - /** @brief Returns the coordinate of the lower boundary BSpline. + /** @brief Returns the coordinate of the lower boundary knot. * - * @return Coordinate of the lower boundary BSpline. + * @return Coordinate of the lower boundary knot. */ KOKKOS_INLINE_FUNCTION ddc::Coordinate rmin() const noexcept { return get_knot(0); } - /** @brief Returns the coordinate of the upper boundary BSpline. + /** @brief Returns the coordinate of the upper boundary knot. * - * @return Coordinate of the upper boundary BSpline. + * @return Coordinate of the upper boundary knot. */ KOKKOS_INLINE_FUNCTION ddc::Coordinate rmax() const noexcept { return get_knot(ncells()); } - /** @brief TODO + /** @brief Returns the length of the domain supporting knots. * - * @return TODO. + * @return The length of the domain supporting knots. */ KOKKOS_INLINE_FUNCTION double length() const noexcept { diff --git a/include/ddc/kernels/splines/bsplines_uniform.hpp b/include/ddc/kernels/splines/bsplines_uniform.hpp index dda44713d..32efa9da3 100644 --- a/include/ddc/kernels/splines/bsplines_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_uniform.hpp @@ -138,6 +138,7 @@ class UniformBSplines : UniformBSplinesBase * The values are computed for every BSplines at the given coordinate x. A spline approximation at coordinate x is a linear combination of those BSplines evaluations weigthed with splines coefficients of the spline-transformed initial discrete function. * @param[out] values The values of the BSplines evaluated at coordinate x. It has to be a (1+degree) 1D mdspan. * @param[in] x The coordinate where BSplines are evaluated. + * @return TODO */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_basis(DSpan1D values, ddc::Coordinate const& x) const @@ -151,6 +152,7 @@ class UniformBSplines : UniformBSplinesBase * The derivatives are computed for every BSplines at the given coordinate x. A spline approximation of a derivative at coordinate x is a linear combination of those BSplines derivatives weigthed with splines coefficients of the spline-transformed initial discrete function. * @param[out] derivs The derivatives of the BSplines evaluated at coordinate x. It has to be a (1+degree) 1D mdspan. * @param[in] x The coordinate where BSplines derivatives are evaluated. + * @return TODO */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_deriv(DSpan1D derivs, ddc::Coordinate const& x) const; @@ -161,6 +163,7 @@ class UniformBSplines : UniformBSplinesBase * @param[out] derivs The values and n derivatives of the BSplines evaluated at coordinate x. It has to be a (1+degree)*(1+n) 2D mdspan. * @param[in] x The coordinates where BSplines derivatives are evaluated. * @param[in] n The number of derivatives to evaluate (in addition to the BSplines values themselves). + * @return TODO */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_basis_and_n_derivs( ddc::DSpan2D derivs, @@ -187,7 +190,7 @@ class UniformBSplines : UniformBSplinesBase return ddc::Coordinate(rmin() + idx * ddc::step()); } - /** @brief Returns the first support knot associated to a DiscreteElement identifying a BSpline. + /** @brief Returns the coordinate of the first support knot associated to a DiscreteElement identifying a BSpline. * * @param[in] ix DiscreteElement identifying the BSpline. * @return Coordinate of the knot. @@ -197,7 +200,7 @@ class UniformBSplines : UniformBSplinesBase return get_knot(ix.uid() - degree()); } - /** @brief Returns the last support knot associated to a DiscreteElement identifying a BSpline. + /** @brief Returns the coordinate of the last support knot associated to a DiscreteElement identifying a BSpline. * * @param[in] ix DiscreteElement identifying the BSpline. * @return Coordinate of the knot. @@ -207,7 +210,7 @@ class UniformBSplines : UniformBSplinesBase return get_knot(ix.uid() + 1); } - /** @brief Returns the \f$n\f$-th knot associated to a discrete_element identifying a BSpline. + /** @brief Returns the coordinate of the \f$n\f$-th knot associated to a discrete_element identifying a BSpline. * * @param[in] ix DiscreteElement identifying the BSpline. * @param[in] n Integer indexing a knot in the support of the BSpline. @@ -218,34 +221,34 @@ class UniformBSplines : UniformBSplinesBase return get_knot(ix.uid() + n - degree()); } - /** @brief Returns the coordinate of the lower boundary BSpline. + /** @brief Returns the coordinate of the lower boundary knot. * - * @return Coordinate of the lower boundary BSpline. + * @return Coordinate of the lower boundary knot. */ KOKKOS_INLINE_FUNCTION ddc::Coordinate rmin() const noexcept { return ddc::coordinate(m_domain.front()); } - /** @brief Returns the coordinate of the upper boundary BSpline. + /** @brief Returns the coordinate of the upper boundary knot. * - * @return Coordinate of the upper boundary BSpline. + * @return Coordinate of the upper boundary knot. */ KOKKOS_INLINE_FUNCTION ddc::Coordinate rmax() const noexcept { return ddc::coordinate(m_domain.back()); } - /** @brief TODO + /** @brief Returns the length of the domain supporting knots. * - * @return TODO. + * @return The length of the domain supporting knots. */ KOKKOS_INLINE_FUNCTION double length() const noexcept { return rmax() - rmin(); } - /** @brief TODO + /** @brief TODO (number of knots ?). * * @return TODO. */ From a563f6dec9db346630a32a91e7a8babb881b0799 Mon Sep 17 00:00:00 2001 From: blegouix Date: Fri, 19 Apr 2024 09:02:04 +0200 Subject: [PATCH 026/189] wip --- .../kernels/splines/bsplines_non_uniform.hpp | 17 +++++++++-------- .../ddc/kernels/splines/bsplines_uniform.hpp | 1 + 2 files changed, 10 insertions(+), 8 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index 6080f053f..29e66878e 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -99,13 +99,6 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase Impl() = default; - template - explicit Impl(Impl const& impl) - : m_domain(impl.m_domain) - , m_nknots(impl.m_nknots) - { - } - /// @brief Construct a `Impl` using a brace-list, i.e. `Impl bsplines({0., 1.})` explicit Impl(std::initializer_list> breaks) : Impl(breaks.begin(), breaks.end()) @@ -122,6 +115,14 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase template Impl(RandomIt breaks_begin, RandomIt breaks_end); + /// @brief Copy-constructs from another Impl with different Kokkos memory space + template + explicit Impl(Impl const& impl) + : m_domain(impl.m_domain) + , m_nknots(impl.m_nknots) + { + } + /// @brief Copy-constructs Impl(Impl const& x) = default; @@ -216,7 +217,7 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase * * @param[in] ix DiscreteElement identifying the BSpline. * @param[in] n Integer indexing a knot in the support of the BSpline. - * @return TODO + * @return Coordinate of the knot. */ KOKKOS_INLINE_FUNCTION ddc::Coordinate get_support_knot_n( discrete_element_type const& ix, diff --git a/include/ddc/kernels/splines/bsplines_uniform.hpp b/include/ddc/kernels/splines/bsplines_uniform.hpp index c94f17f39..cfab54dcf 100644 --- a/include/ddc/kernels/splines/bsplines_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_uniform.hpp @@ -218,6 +218,7 @@ class UniformBSplines : detail::UniformBSplinesBase * * @param[in] ix DiscreteElement identifying the BSpline. * @param[in] n Integer indexing a knot in the support of the BSpline. + * @return Coordinate of the knot. */ KOKKOS_INLINE_FUNCTION double get_support_knot_n(discrete_element_type const& ix, int n) const From 70172346a26721f023620e04ad15a60d2296985e Mon Sep 17 00:00:00 2001 From: blegouix Date: Fri, 19 Apr 2024 09:11:13 +0200 Subject: [PATCH 027/189] fix for allowing doxygen to keep track of integrals() --- include/ddc/kernels/splines/bsplines_non_uniform.hpp | 4 ++-- include/ddc/kernels/splines/bsplines_uniform.hpp | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index 29e66878e..5d8fcfbb2 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -593,9 +593,9 @@ KOKKOS_INLINE_FUNCTION int NonUniformBSplines::Impl:: template template template -KOKKOS_INLINE_FUNCTION ddc::ChunkSpan, Layout, MemorySpace2> +KOKKOS_INLINE_FUNCTION ddc::ChunkSpan::Impl::discrete_domain_type, Layout, MemorySpace2> NonUniformBSplines::Impl::integrals( - ddc::ChunkSpan, Layout, MemorySpace2> int_vals) const + ddc::ChunkSpan::Impl::discrete_domain_type, Layout, MemorySpace2> int_vals) const { if constexpr (is_periodic()) { assert(int_vals.size() == nbasis() || int_vals.size() == size()); diff --git a/include/ddc/kernels/splines/bsplines_uniform.hpp b/include/ddc/kernels/splines/bsplines_uniform.hpp index cfab54dcf..49ab7703d 100644 --- a/include/ddc/kernels/splines/bsplines_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_uniform.hpp @@ -523,9 +523,9 @@ KOKKOS_INLINE_FUNCTION void UniformBSplines::Impl::ge template template template -KOKKOS_INLINE_FUNCTION ddc::ChunkSpan, Layout, MemorySpace2> +KOKKOS_INLINE_FUNCTION ddc::ChunkSpan::Impl::discrete_domain_type, Layout, MemorySpace2> UniformBSplines::Impl::integrals( - ddc::ChunkSpan, Layout, MemorySpace2> int_vals) const + ddc::ChunkSpan::Impl::discrete_domain_type, Layout, MemorySpace2> int_vals) const { if constexpr (is_periodic()) { assert(int_vals.size() == nbasis() || int_vals.size() == size()); From dcc5c6f4d8d62086f775bdbb4e81483734a481ee Mon Sep 17 00:00:00 2001 From: blegouix Date: Fri, 19 Apr 2024 09:11:59 +0200 Subject: [PATCH 028/189] format --- include/ddc/kernels/splines/bsplines_non_uniform.hpp | 12 ++++++++++-- include/ddc/kernels/splines/bsplines_uniform.hpp | 12 ++++++++++-- 2 files changed, 20 insertions(+), 4 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index 5d8fcfbb2..bbf1b1217 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -593,9 +593,17 @@ KOKKOS_INLINE_FUNCTION int NonUniformBSplines::Impl:: template template template -KOKKOS_INLINE_FUNCTION ddc::ChunkSpan::Impl::discrete_domain_type, Layout, MemorySpace2> +KOKKOS_INLINE_FUNCTION ddc::ChunkSpan< + double, + typename NonUniformBSplines::Impl::discrete_domain_type, + Layout, + MemorySpace2> NonUniformBSplines::Impl::integrals( - ddc::ChunkSpan::Impl::discrete_domain_type, Layout, MemorySpace2> int_vals) const + ddc::ChunkSpan< + double, + typename NonUniformBSplines::Impl::discrete_domain_type, + Layout, + MemorySpace2> int_vals) const { if constexpr (is_periodic()) { assert(int_vals.size() == nbasis() || int_vals.size() == size()); diff --git a/include/ddc/kernels/splines/bsplines_uniform.hpp b/include/ddc/kernels/splines/bsplines_uniform.hpp index 49ab7703d..2a3344691 100644 --- a/include/ddc/kernels/splines/bsplines_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_uniform.hpp @@ -523,9 +523,17 @@ KOKKOS_INLINE_FUNCTION void UniformBSplines::Impl::ge template template template -KOKKOS_INLINE_FUNCTION ddc::ChunkSpan::Impl::discrete_domain_type, Layout, MemorySpace2> +KOKKOS_INLINE_FUNCTION ddc::ChunkSpan< + double, + typename UniformBSplines::Impl::discrete_domain_type, + Layout, + MemorySpace2> UniformBSplines::Impl::integrals( - ddc::ChunkSpan::Impl::discrete_domain_type, Layout, MemorySpace2> int_vals) const + ddc::ChunkSpan< + double, + typename UniformBSplines::Impl::discrete_domain_type, + Layout, + MemorySpace2> int_vals) const { if constexpr (is_periodic()) { assert(int_vals.size() == nbasis() || int_vals.size() == size()); From 8f7f760efde697f4c36e146ef1273a2c565a31ee Mon Sep 17 00:00:00 2001 From: blegouix Date: Fri, 19 Apr 2024 09:50:34 +0200 Subject: [PATCH 029/189] Revert "fix for allowing doxygen to keep track of integrals()" This reverts commit 70172346a26721f023620e04ad15a60d2296985e. --- include/ddc/kernels/splines/bsplines_non_uniform.hpp | 12 ++---------- include/ddc/kernels/splines/bsplines_uniform.hpp | 12 ++---------- 2 files changed, 4 insertions(+), 20 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index bbf1b1217..29e66878e 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -593,17 +593,9 @@ KOKKOS_INLINE_FUNCTION int NonUniformBSplines::Impl:: template template template -KOKKOS_INLINE_FUNCTION ddc::ChunkSpan< - double, - typename NonUniformBSplines::Impl::discrete_domain_type, - Layout, - MemorySpace2> +KOKKOS_INLINE_FUNCTION ddc::ChunkSpan, Layout, MemorySpace2> NonUniformBSplines::Impl::integrals( - ddc::ChunkSpan< - double, - typename NonUniformBSplines::Impl::discrete_domain_type, - Layout, - MemorySpace2> int_vals) const + ddc::ChunkSpan, Layout, MemorySpace2> int_vals) const { if constexpr (is_periodic()) { assert(int_vals.size() == nbasis() || int_vals.size() == size()); diff --git a/include/ddc/kernels/splines/bsplines_uniform.hpp b/include/ddc/kernels/splines/bsplines_uniform.hpp index 2a3344691..cfab54dcf 100644 --- a/include/ddc/kernels/splines/bsplines_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_uniform.hpp @@ -523,17 +523,9 @@ KOKKOS_INLINE_FUNCTION void UniformBSplines::Impl::ge template template template -KOKKOS_INLINE_FUNCTION ddc::ChunkSpan< - double, - typename UniformBSplines::Impl::discrete_domain_type, - Layout, - MemorySpace2> +KOKKOS_INLINE_FUNCTION ddc::ChunkSpan, Layout, MemorySpace2> UniformBSplines::Impl::integrals( - ddc::ChunkSpan< - double, - typename UniformBSplines::Impl::discrete_domain_type, - Layout, - MemorySpace2> int_vals) const + ddc::ChunkSpan, Layout, MemorySpace2> int_vals) const { if constexpr (is_periodic()) { assert(int_vals.size() == nbasis() || int_vals.size() == size()); From 9d675c94d77c3dc96ea9880f2f60d3b834004dbf Mon Sep 17 00:00:00 2001 From: blegouix Date: Fri, 19 Apr 2024 10:30:31 +0200 Subject: [PATCH 030/189] autoreview --- include/ddc/kernels/splines/bsplines_non_uniform.hpp | 10 +++++----- include/ddc/kernels/splines/bsplines_uniform.hpp | 10 +++++----- 2 files changed, 10 insertions(+), 10 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index 29e66878e..02cf29dd9 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -70,7 +70,7 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase return false; } - /// @brief Impl + /// @brief Impl TODO template class Impl { @@ -85,13 +85,13 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase int m_nknots; public: - /// @brief The type of discrete dimension identifying BSplines. + /// @brief The type of discrete dimension representing the BSplines. using discrete_dimension_type = NonUniformBSplines; - /// @brief The type of discrete domain indexing the BSplines. + /// @brief The type of discrete domain identifying the BSplines. using discrete_domain_type = DiscreteDomain; - /// @brief The type of discrete element indexing a BSpline. + /// @brief The type of discrete element identifying a BSpline. using discrete_element_type = DiscreteElement; /// @brief The type of discrete vector representing an "indexes displacement" between two BSplines. @@ -213,7 +213,7 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase return ddc::coordinate(ddc::DiscreteElement(ix.uid() + degree() + 1)); } - /** @brief Returns the coordinate of the \f$n\f$-th knot associated to a discrete_element identifying a BSpline. + /** @brief Returns the coordinate of the \f$n\f$-th knot associated to a DiscreteElement identifying a BSpline. * * @param[in] ix DiscreteElement identifying the BSpline. * @param[in] n Integer indexing a knot in the support of the BSpline. diff --git a/include/ddc/kernels/splines/bsplines_uniform.hpp b/include/ddc/kernels/splines/bsplines_uniform.hpp index cfab54dcf..8efb291ee 100644 --- a/include/ddc/kernels/splines/bsplines_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_uniform.hpp @@ -70,7 +70,7 @@ class UniformBSplines : detail::UniformBSplinesBase return true; } - /// @brief Impl + /// @brief Impl TODO template class Impl { @@ -84,13 +84,13 @@ class UniformBSplines : detail::UniformBSplinesBase ddc::DiscreteDomain m_domain; public: - /// @brief The type of discrete dimension identifying BSplines. + /// @brief The type of discrete dimension representing the BSplines. using discrete_dimension_type = UniformBSplines; - /// @brief The type of discrete domain indexing the BSplines. + /// @brief The type of discrete domain identifying the BSplines. using discrete_domain_type = DiscreteDomain; - /// @brief The type of discrete element indexing a BSpline. + /// @brief The type of discrete element identifying a BSpline. using discrete_element_type = DiscreteElement; /// @brief The type of discrete vector representing an "indexes displacement" between two BSplines. @@ -214,7 +214,7 @@ class UniformBSplines : detail::UniformBSplinesBase return get_knot(ix.uid() + 1); } - /** @brief Returns the coordinate of the \f$n\f$-th knot associated to a discrete_element identifying a BSpline. + /** @brief Returns the coordinate of the \f$n\f$-th knot associated to a DiscreteElement identifying a BSpline. * * @param[in] ix DiscreteElement identifying the BSpline. * @param[in] n Integer indexing a knot in the support of the BSpline. From 6850ae90fa8dff82d28b825d1ba27de385c50d3e Mon Sep 17 00:00:00 2001 From: blegouix Date: Fri, 19 Apr 2024 10:50:31 +0200 Subject: [PATCH 031/189] B-splines --- .../kernels/splines/bsplines_non_uniform.hpp | 74 ++++++++--------- .../ddc/kernels/splines/bsplines_uniform.hpp | 79 +++++++++---------- 2 files changed, 76 insertions(+), 77 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index 02cf29dd9..85df1f5fd 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -29,10 +29,10 @@ struct NonUniformBSplinesBase } // namespace detail /** - * The type of a non-uniform BSplines 1D basis. + * The type of a non-uniform B-splines 1D basis. * - * @tparam Tag The tag identifying the continuous dimension which supports the building of the BSplines. - * @tparam D The degree of the BSplines. + * @tparam Tag The tag identifying the continuous dimension which supports the building of the B-splines. + * @tparam D The degree of the B-splines. */ template class NonUniformBSplines : detail::NonUniformBSplinesBase @@ -40,31 +40,31 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase static_assert(D > 0, "Parameter `D` must be positive"); public: - /// @brief The tag identifying the continuous dimension which supports the building of the BSplines. + /// @brief The tag identifying the continuous dimension which supports the building of the B-splines. using tag_type = Tag; - /// @brief The discrete dimension identifying BSplines. + /// @brief The discrete dimension identifying B-splines. using discrete_dimension_type = NonUniformBSplines; - /// @brief The degree of BSplines. + /// @brief The degree of B-splines. static constexpr std::size_t degree() noexcept { return D; } - /// @brief Indicates if the BSplines are periodic or not. + /// @brief Indicates if the B-splines are periodic or not. static constexpr bool is_periodic() noexcept { return Tag::PERIODIC; } - /// @brief Indicates if the BSplines are radial or not (should be deprecated soon because this concept is not in the scope of DDC). + /// @brief Indicates if the B-splines are radial or not (should be deprecated soon because this concept is not in the scope of DDC). static constexpr bool is_radial() noexcept { return false; } - /// @brief Indicates if the BSplines are uniform or not (this is not the case here). + /// @brief Indicates if the B-splines are uniform or not (this is not the case here). static constexpr bool is_uniform() noexcept { return false; @@ -85,16 +85,16 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase int m_nknots; public: - /// @brief The type of discrete dimension representing the BSplines. + /// @brief The type of discrete dimension representing the B-splines. using discrete_dimension_type = NonUniformBSplines; - /// @brief The type of discrete domain identifying the BSplines. + /// @brief The type of discrete domain identifying the B-splines. using discrete_domain_type = DiscreteDomain; - /// @brief The type of discrete element identifying a BSpline. + /// @brief The type of discrete element identifying a B-spline. using discrete_element_type = DiscreteElement; - /// @brief The type of discrete vector representing an "indexes displacement" between two BSplines. + /// @brief The type of discrete vector representing an "indexes displacement" between two B-splines. using discrete_vector_type = DiscreteVector; Impl() = default; @@ -138,32 +138,32 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase /// @brief Move-assigns Impl& operator=(Impl&& x) = default; - /** @brief Evaluates BSplines at a given coordinate + /** @brief Evaluates B-splines at a given coordinate * - * The values are computed for every BSplines at the given coordinate x. A spline approximation at coordinate x is a linear combination of those BSplines evaluations weigthed with splines coefficients of the spline-transformed initial discrete function. - * @param[out] values The values of the BSplines evaluated at coordinate x. It has to be a (1+degree) 1D mdspan. - * @param[in] x The coordinate where BSplines are evaluated. + * The values are computed for every B-splines at the given coordinate x. A spline approximation at coordinate x is a linear combination of those B-splines evaluations weigthed with splines coefficients of the spline-transformed initial discrete function. + * @param[out] values The values of the B-splines evaluated at coordinate x. It has to be a (1+degree) 1D mdspan. + * @param[in] x The coordinate where B-splines are evaluated. * @return TODO */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_basis(DSpan1D values, ddc::Coordinate const& x) const; - /** @brief Evaluates BSplines derivatives at a given coordinate + /** @brief Evaluates B-splines derivatives at a given coordinate * - * The derivatives are computed for every BSplines at the given coordinate x. A spline approximation of a derivative at coordinate x is a linear combination of those BSplines derivatives weigthed with splines coefficients of the spline-transformed initial discrete function. - * @param[out] derivs The derivatives of the BSplines evaluated at coordinate x. It has to be a (1+degree) 1D mdspan. - * @param[in] x The coordinate where BSplines derivatives are evaluated. + * The derivatives are computed for every B-splines at the given coordinate x. A spline approximation of a derivative at coordinate x is a linear combination of those B-splines derivatives weigthed with splines coefficients of the spline-transformed initial discrete function. + * @param[out] derivs The derivatives of the B-splines evaluated at coordinate x. It has to be a (1+degree) 1D mdspan. + * @param[in] x The coordinate where B-splines derivatives are evaluated. * @return TODO */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_deriv(DSpan1D derivs, ddc::Coordinate const& x) const; - /** @brief Evaluates BSplines values and n derivatives at a given coordinate + /** @brief Evaluates B-splines values and n derivatives at a given coordinate * - * The values and derivatives are computed for every BSplines at the given coordinate x. - * @param[out] derivs The values and n derivatives of the BSplines evaluated at coordinate x. It has to be a (1+degree)*(1+n) 2D mdspan. - * @param[in] x The coordinates where BSplines derivatives are evaluated. - * @param[in] n The number of derivatives to evaluate (in addition to the BSplines values themselves). + * The values and derivatives are computed for every B-splines at the given coordinate x. + * @param[out] derivs The values and n derivatives of the B-splines evaluated at coordinate x. It has to be a (1+degree)*(1+n) 2D mdspan. + * @param[in] x The coordinates where B-splines derivatives are evaluated. + * @param[in] n The number of derivatives to evaluate (in addition to the B-splines values themselves). * @return TODO */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_basis_and_n_derivs( @@ -171,7 +171,7 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase ddc::Coordinate const& x, std::size_t n) const; - /** @brief Compute the integrals of the BSplines. + /** @brief Compute the integrals of the B-splines. * * @param[out] int_vals The values of the integrals. It has to be a (1+nbasis) 1D mdspan. * @return The values of the integrals. @@ -181,7 +181,7 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase integrals( ddc::ChunkSpan int_vals) const; - /** @brief Returns the coordinate of the knot corresponding to the given index for a BSpline. + /** @brief Returns the coordinate of the knot corresponding to the given index for a B-spline. * * @param[in] knot_idx Integer identifying index of the knot. * @return Coordinate of the knot. @@ -191,9 +191,9 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase return ddc::coordinate(ddc::DiscreteElement(knot_idx + degree())); } - /** @brief Returns the coordinate of the first support knot associated to a discrete_element identifying a BSpline. + /** @brief Returns the coordinate of the first support knot associated to a discrete_element identifying a B-spline. * - * @param[in] ix DiscreteElement identifying the BSpline. + * @param[in] ix DiscreteElement identifying the B-spline. * @return Coordinate of the knot. */ KOKKOS_INLINE_FUNCTION ddc::Coordinate get_first_support_knot( @@ -202,9 +202,9 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase return ddc::coordinate(ddc::DiscreteElement(ix.uid())); } - /** @brief Returns the coordinate of the last support knot associated to a discrete_element identifying a BSpline. + /** @brief Returns the coordinate of the last support knot associated to a discrete_element identifying a B-spline. * - * @param[in] ix DiscreteElement identifying the BSpline. + * @param[in] ix DiscreteElement identifying the B-spline. * @return Coordinate of the knot. */ KOKKOS_INLINE_FUNCTION ddc::Coordinate get_last_support_knot( @@ -213,10 +213,10 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase return ddc::coordinate(ddc::DiscreteElement(ix.uid() + degree() + 1)); } - /** @brief Returns the coordinate of the \f$n\f$-th knot associated to a DiscreteElement identifying a BSpline. + /** @brief Returns the coordinate of the \f$n\f$-th knot associated to a DiscreteElement identifying a B-spline. * - * @param[in] ix DiscreteElement identifying the BSpline. - * @param[in] n Integer indexing a knot in the support of the BSpline. + * @param[in] ix DiscreteElement identifying the B-spline. + * @param[in] n Integer indexing a knot in the support of the B-spline. * @return Coordinate of the knot. */ KOKKOS_INLINE_FUNCTION ddc::Coordinate get_support_knot_n( @@ -309,9 +309,9 @@ struct is_non_uniform_bsplines : public std::is_base_of constexpr bool is_non_uniform_bsplines_v = is_non_uniform_bsplines::value; diff --git a/include/ddc/kernels/splines/bsplines_uniform.hpp b/include/ddc/kernels/splines/bsplines_uniform.hpp index 8efb291ee..bd0354dbd 100644 --- a/include/ddc/kernels/splines/bsplines_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_uniform.hpp @@ -29,10 +29,10 @@ struct UniformBSplinesBase } // namespace detail /** - * The type of a uniform BSplines 1D basis. + * The type of a uniform B-splines 1D basis. * - * @tparam Tag The tag identifying the continuous dimension which supports the building of the BSplines. - * @tparam D The degree of the BSplines. + * @tparam Tag The tag identifying the continuous dimension which supports the building of the B-splines. + * @tparam D The degree of the B-splines. */ template class UniformBSplines : detail::UniformBSplinesBase @@ -40,31 +40,31 @@ class UniformBSplines : detail::UniformBSplinesBase static_assert(D > 0, "Parameter `D` must be positive"); public: - /// @brief The tag identifying the continuous dimension which supports the building of the BSplines. + /// @brief The tag identifying the continuous dimension which supports the building of the B-splines. using tag_type = Tag; - /// @brief The discrete dimension representing BSplines. + /// @brief The discrete dimension representing B-splines. using discrete_dimension_type = UniformBSplines; - /// @brief The degree of BSplines. + /// @brief The degree of B-splines. static constexpr std::size_t degree() noexcept { return D; } - /// @brief Indicates if the BSplines are periodic or not. + /// @brief Indicates if the B-splines are periodic or not. static constexpr bool is_periodic() noexcept { return Tag::PERIODIC; } - /// @brief Indicates if the BSplines are radial or not (should be deprecated soon because this concept is not in the scope of DDC). + /// @brief Indicates if the B-splines are radial or not (should be deprecated soon because this concept is not in the scope of DDC). static constexpr bool is_radial() noexcept { return false; } - /// @brief Indicates if the BSplines are uniform or not (this is the case here). + /// @brief Indicates if the B-splines are uniform or not (this is the case here). static constexpr bool is_uniform() noexcept { return true; @@ -84,21 +84,21 @@ class UniformBSplines : detail::UniformBSplinesBase ddc::DiscreteDomain m_domain; public: - /// @brief The type of discrete dimension representing the BSplines. + /// @brief The type of discrete dimension representing the B-splines. using discrete_dimension_type = UniformBSplines; - /// @brief The type of discrete domain identifying the BSplines. + /// @brief The type of discrete domain identifying the B-splines. using discrete_domain_type = DiscreteDomain; - /// @brief The type of discrete element identifying a BSpline. + /// @brief The type of discrete element identifying a B-spline. using discrete_element_type = DiscreteElement; - /// @brief The type of discrete vector representing an "indexes displacement" between two BSplines. + /// @brief The type of discrete vector representing an "indexes displacement" between two B-splines. using discrete_vector_type = DiscreteVector; Impl() = default; - /** Constructs a BSplines basis with n equidistant knots over \f$[a, b]\f$ + /** Constructs a B-splines basis with n equidistant knots over \f$[a, b]\f$ * * @param rmin the real ddc::coordinate of the first knot * @param rmax the real ddc::coordinate of the last knot @@ -137,11 +137,11 @@ class UniformBSplines : detail::UniformBSplinesBase /// @brief Move-assigns Impl& operator=(Impl&& x) = default; - /** @brief Evaluates BSplines at a given coordinate + /** @brief Evaluates B-splines at a given coordinate * - * The values are computed for every BSplines at the given coordinate x. A spline approximation at coordinate x is a linear combination of those BSplines evaluations weigthed with splines coefficients of the spline-transformed initial discrete function. - * @param[out] values The values of the BSplines evaluated at coordinate x. It has to be a (1+degree) 1D mdspan. - * @param[in] x The coordinate where BSplines are evaluated. + * The values are computed for every B-splines at the given coordinate x. A spline approximation at coordinate x is a linear combination of those B-splines evaluations weigthed with splines coefficients of the spline-transformed initial discrete function. + * @param[out] values The values of the B-splines evaluated at coordinate x. It has to be a (1+degree) 1D mdspan. + * @param[in] x The coordinate where B-splines are evaluated. * @return TODO */ KOKKOS_INLINE_FUNCTION discrete_element_type @@ -151,22 +151,22 @@ class UniformBSplines : detail::UniformBSplinesBase return eval_basis(values, x, degree()); } - /** @brief Evaluates BSplines derivatives at a given coordinate + /** @brief Evaluates B-splines derivatives at a given coordinate * - * The derivatives are computed for every BSplines at the given coordinate x. A spline approximation of a derivative at coordinate x is a linear combination of those BSplines derivatives weigthed with splines coefficients of the spline-transformed initial discrete function. - * @param[out] derivs The derivatives of the BSplines evaluated at coordinate x. It has to be a (1+degree) 1D mdspan. - * @param[in] x The coordinate where BSplines derivatives are evaluated. + * The derivatives are computed for every B-splines at the given coordinate x. A spline approximation of a derivative at coordinate x is a linear combination of those B-splines derivatives weigthed with splines coefficients of the spline-transformed initial discrete function. + * @param[out] derivs The derivatives of the B-splines evaluated at coordinate x. It has to be a (1+degree) 1D mdspan. + * @param[in] x The coordinate where B-splines derivatives are evaluated. * @return TODO */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_deriv(DSpan1D derivs, ddc::Coordinate const& x) const; - /** @brief Evaluates BSplines values and \f$n\f$ derivatives at a given coordinate + /** @brief Evaluates B-splines values and \f$n\f$ derivatives at a given coordinate * - * The values and derivatives are computed for every BSplines at the given coordinate x. - * @param[out] derivs The values and n derivatives of the BSplines evaluated at coordinate x. It has to be a (1+degree)*(1+n) 2D mdspan. - * @param[in] x The coordinates where BSplines derivatives are evaluated. - * @param[in] n The number of derivatives to evaluate (in addition to the BSplines values themselves). + * The values and derivatives are computed for every B-splines at the given coordinate x. + * @param[out] derivs The values and n derivatives of the B-splines evaluated at coordinate x. It has to be a (1+degree)*(1+n) 2D mdspan. + * @param[in] x The coordinates where B-splines derivatives are evaluated. + * @param[in] n The number of derivatives to evaluate (in addition to the B-splines values themselves). * @return TODO */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_basis_and_n_derivs( @@ -174,7 +174,7 @@ class UniformBSplines : detail::UniformBSplinesBase ddc::Coordinate const& x, std::size_t n) const; - /** @brief Compute the integrals of the BSplines. + /** @brief Compute the integrals of the B-splines. * * @param[out] int_vals The values of the integrals. It has to be a (1+nbasis) 1D mdspan. * @return The values of the integrals. @@ -184,7 +184,7 @@ class UniformBSplines : detail::UniformBSplinesBase integrals( ddc::ChunkSpan int_vals) const; - /** @brief Returns the coordinate of the knot corresponding to the given index for a BSpline. + /** @brief Returns the coordinate of the knot corresponding to the given index for a B-spline. * * @param[in] idx Integer identifying index of the knot. * @return Coordinate of the knot. @@ -194,9 +194,9 @@ class UniformBSplines : detail::UniformBSplinesBase return ddc::Coordinate(rmin() + idx * ddc::step()); } - /** @brief Returns the coordinate of the first support knot associated to a DiscreteElement identifying a BSpline. + /** @brief Returns the coordinate of the first support knot associated to a DiscreteElement identifying a B-spline. * - * @param[in] ix DiscreteElement identifying the BSpline. + * @param[in] ix DiscreteElement identifying the B-spline. * @return Coordinate of the knot. */ KOKKOS_INLINE_FUNCTION double get_first_support_knot(discrete_element_type const& ix) const @@ -204,9 +204,9 @@ class UniformBSplines : detail::UniformBSplinesBase return get_knot(ix.uid() - degree()); } - /** @brief Returns the coordinate of the last support knot associated to a DiscreteElement identifying a BSpline. + /** @brief Returns the coordinate of the last support knot associated to a DiscreteElement identifying a B-spline. * - * @param[in] ix DiscreteElement identifying the BSpline. + * @param[in] ix DiscreteElement identifying the B-spline. * @return Coordinate of the knot. */ KOKKOS_INLINE_FUNCTION double get_last_support_knot(discrete_element_type const& ix) const @@ -214,10 +214,10 @@ class UniformBSplines : detail::UniformBSplinesBase return get_knot(ix.uid() + 1); } - /** @brief Returns the coordinate of the \f$n\f$-th knot associated to a DiscreteElement identifying a BSpline. + /** @brief Returns the coordinate of the \f$n\f$-th knot associated to a DiscreteElement identifying a B-spline. * - * @param[in] ix DiscreteElement identifying the BSpline. - * @param[in] n Integer indexing a knot in the support of the BSpline. + * @param[in] ix DiscreteElement identifying the B-spline. + * @param[in] n Integer indexing a knot in the support of the B-spline. * @return Coordinate of the knot. */ KOKKOS_INLINE_FUNCTION double get_support_knot_n(discrete_element_type const& ix, int n) @@ -311,9 +311,9 @@ struct is_uniform_bsplines : public std::is_base_of constexpr bool is_uniform_bsplines_v = is_uniform_bsplines::value; @@ -426,8 +426,7 @@ KOKKOS_INLINE_FUNCTION ddc::DiscreteElement UniformBSplines::Impl< // 2. Compute index range of B-splines with support over cell 'icell' get_icell_and_offset(jmin, offset, x); - // 3. Recursively evaluate B-splines (see - // "sll_s_uniform_BSplines_eval_basis") + // 3. Recursively evaluate B-splines (eval_basis) // up to self%degree, and store them all in the upper-right triangle of // ndu double xx, temp, saved; From 937d4326fc94531aeb1a518631e809f0a406bc73 Mon Sep 17 00:00:00 2001 From: Baptiste Legouix Date: Fri, 19 Apr 2024 10:52:51 +0200 Subject: [PATCH 032/189] Update include/ddc/kernels/splines/bsplines_non_uniform.hpp Co-authored-by: EmilyBourne --- include/ddc/kernels/splines/bsplines_non_uniform.hpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index 02cf29dd9..68ad173f6 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -94,7 +94,7 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase /// @brief The type of discrete element identifying a BSpline. using discrete_element_type = DiscreteElement; - /// @brief The type of discrete vector representing an "indexes displacement" between two BSplines. + /// @brief The type of a discrete vector representing an "index displacement" between two B-splines. using discrete_vector_type = DiscreteVector; Impl() = default; From 9ffbe0439cc6e6f64ac9595aca528072b9574e3c Mon Sep 17 00:00:00 2001 From: blegouix Date: Fri, 19 Apr 2024 10:55:06 +0200 Subject: [PATCH 033/189] emily's review --- include/ddc/kernels/splines/bsplines_non_uniform.hpp | 8 ++++---- include/ddc/kernels/splines/bsplines_uniform.hpp | 8 ++++---- 2 files changed, 8 insertions(+), 8 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index 85df1f5fd..b93e9b11e 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -85,16 +85,16 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase int m_nknots; public: - /// @brief The type of discrete dimension representing the B-splines. + /// @brief The type of the discrete dimension representing the B-splines. using discrete_dimension_type = NonUniformBSplines; - /// @brief The type of discrete domain identifying the B-splines. + /// @brief The type of a discrete domain identifying the B-splines. using discrete_domain_type = DiscreteDomain; - /// @brief The type of discrete element identifying a B-spline. + /// @brief The type of a discrete element identifying a B-spline. using discrete_element_type = DiscreteElement; - /// @brief The type of discrete vector representing an "indexes displacement" between two B-splines. + /// @brief The type of a discrete vector representing an "index displacement" between two B-splines. using discrete_vector_type = DiscreteVector; Impl() = default; diff --git a/include/ddc/kernels/splines/bsplines_uniform.hpp b/include/ddc/kernels/splines/bsplines_uniform.hpp index bd0354dbd..2cf34afad 100644 --- a/include/ddc/kernels/splines/bsplines_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_uniform.hpp @@ -84,16 +84,16 @@ class UniformBSplines : detail::UniformBSplinesBase ddc::DiscreteDomain m_domain; public: - /// @brief The type of discrete dimension representing the B-splines. + /// @brief The type of the discrete dimension representing the B-splines. using discrete_dimension_type = UniformBSplines; - /// @brief The type of discrete domain identifying the B-splines. + /// @brief The type of a discrete domain identifying the B-splines. using discrete_domain_type = DiscreteDomain; - /// @brief The type of discrete element identifying a B-spline. + /// @brief The type of a discrete element identifying a B-spline. using discrete_element_type = DiscreteElement; - /// @brief The type of discrete vector representing an "indexes displacement" between two B-splines. + /// @brief The type of a discrete vector representing an "index displacement" between two B-splines. using discrete_vector_type = DiscreteVector; Impl() = default; From 8c5c579841ac3c2a4b91ca941f09eaeb714472e5 Mon Sep 17 00:00:00 2001 From: blegouix Date: Fri, 19 Apr 2024 13:51:24 +0200 Subject: [PATCH 034/189] wip --- .../kernels/splines/bsplines_non_uniform.hpp | 75 +++++++++++++------ .../ddc/kernels/splines/bsplines_uniform.hpp | 71 +++++++++++++----- 2 files changed, 106 insertions(+), 40 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index b93e9b11e..34b19f826 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -31,7 +31,7 @@ struct NonUniformBSplinesBase /** * The type of a non-uniform B-splines 1D basis. * - * @tparam Tag The tag identifying the continuous dimension which supports the building of the B-splines. + * @tparam Tag The tag identifying the continuous dimension on which the support of the B-spline functions are defined. * @tparam D The degree of the B-splines. */ template @@ -40,7 +40,7 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase static_assert(D > 0, "Parameter `D` must be positive"); public: - /// @brief The tag identifying the continuous dimension which supports the building of the B-splines. + /// @brief The tag identifying the continuous dimension on which the support of the B-splines are defined. using tag_type = Tag; /// @brief The discrete dimension identifying B-splines. @@ -88,7 +88,7 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase /// @brief The type of the discrete dimension representing the B-splines. using discrete_dimension_type = NonUniformBSplines; - /// @brief The type of a discrete domain identifying the B-splines. + /// @brief The type of a discrete domain whose elements identify the B-splines. using discrete_domain_type = DiscreteDomain; /// @brief The type of a discrete element identifying a B-spline. @@ -138,33 +138,48 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase /// @brief Move-assigns Impl& operator=(Impl&& x) = default; - /** @brief Evaluates B-splines at a given coordinate + /** @brief Evaluates non-zero B-splines at a given coordinate. * - * The values are computed for every B-splines at the given coordinate x. A spline approximation at coordinate x is a linear combination of those B-splines evaluations weigthed with splines coefficients of the spline-transformed initial discrete function. - * @param[out] values The values of the B-splines evaluated at coordinate x. It has to be a (1+degree) 1D mdspan. + * The values are computed for every B-spline with support at the given coordinate x. There are only (degree+1) + * B-splines which are non-zero at any given point. It is these B-splines which are evaluated. + * This can be useful to calculate a spline approximation of a function. A spline approximation at coordinate x + * is a linear combination of these B-spline evaluations weighted with spline coefficients of the spline-transformed + * initial discrete function. + * + * @param[out] values The values of the B-splines evaluated at coordinate x. It has to be a 1D mdspan with (degree+1) elements. * @param[in] x The coordinate where B-splines are evaluated. - * @return TODO + * @return The index of the first B-spline which is evaluated. */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_basis(DSpan1D values, ddc::Coordinate const& x) const; - /** @brief Evaluates B-splines derivatives at a given coordinate + /** @brief Evaluates non-zero B-splines derivatives at a given coordinate + * + * The derivatives are computed for every B-splines with support at the given coordinate x. There are only (degree+1) + * B-splines which are non-zero at any given point. It is these B-splines which are derivated. + * A spline approximation of a derivative at coordinate x is a linear + * combination of those B-splines derivatives weigthed with splines coefficients of the spline-transformed + * initial discrete function. * - * The derivatives are computed for every B-splines at the given coordinate x. A spline approximation of a derivative at coordinate x is a linear combination of those B-splines derivatives weigthed with splines coefficients of the spline-transformed initial discrete function. - * @param[out] derivs The derivatives of the B-splines evaluated at coordinate x. It has to be a (1+degree) 1D mdspan. + * @param[out] derivs The derivatives of the B-splines evaluated at coordinate x. It has to be a 1D mdspan with (degree+1) elements. * @param[in] x The coordinate where B-splines derivatives are evaluated. - * @return TODO + * @return The index of the first B-spline which is derivated. */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_deriv(DSpan1D derivs, ddc::Coordinate const& x) const; - /** @brief Evaluates B-splines values and n derivatives at a given coordinate + /** @brief Evaluates non-zero B-splines values and \f$n\f$ derivatives at a given coordinate + * + * The values and derivatives are computed for every B-splines with support at the given coordinate x. There are only (degree+1) + * B-splines which are non-zero at any given point. It is these B-splines which are derivated. + * A spline approximation of a derivative at coordinate x is a linear + * combination of those B-splines derivatives weigthed with splines coefficients of the spline-transformed + * initial discrete function. * - * The values and derivatives are computed for every B-splines at the given coordinate x. - * @param[out] derivs The values and n derivatives of the B-splines evaluated at coordinate x. It has to be a (1+degree)*(1+n) 2D mdspan. - * @param[in] x The coordinates where B-splines derivatives are evaluated. + * @param[out] derivs The values and \f$n\f$ derivatives of the B-splines evaluated at coordinate x. It has to be a 2D mdspan with (degree+1)*(n+1) elements. + * @param[in] x The coordinate where B-splines derivatives are evaluated. * @param[in] n The number of derivatives to evaluate (in addition to the B-splines values themselves). - * @return TODO + * @return The index of the first B-spline which is evaluated/derivated. */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_basis_and_n_derivs( ddc::DSpan2D derivs, @@ -173,7 +188,9 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase /** @brief Compute the integrals of the B-splines. * - * @param[out] int_vals The values of the integrals. It has to be a (1+nbasis) 1D mdspan. + * The integral of each of the B-splines over their support within the domain on which this basis was defined. + * + * @param[out] int_vals The values of the integrals. It has to be a (nbasis) 1D mdspan. * @return The values of the integrals. */ template @@ -181,7 +198,12 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase integrals( ddc::ChunkSpan int_vals) const; - /** @brief Returns the coordinate of the knot corresponding to the given index for a B-spline. + /** @brief Returns the coordinate of the knot corresponding to the given index. + * + * Returns the coordinate of the knot corresponding to the given index for a B-spline. The domain + * over which the B-splines are defined is comprised of ncells+1 knots however there are a total of + * ncells+1+2*degree knots. The additional knots which control the shape of the B-splines near the + * boundary are added before and after the break points. The knot index is therefore in the interval [-degree, ncells+degree] * * @param[in] knot_idx Integer identifying index of the knot. * @return Coordinate of the knot. @@ -191,7 +213,11 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase return ddc::coordinate(ddc::DiscreteElement(knot_idx + degree())); } - /** @brief Returns the coordinate of the first support knot associated to a discrete_element identifying a B-spline. + /** @brief Returns the coordinate of the first support knot associated to a DiscreteElement identifying a B-spline. + * + * Each B-spline has a support defined over (degree+2) knots. For a B-spline identified by the + * provided DiscreteElement, this function returns the first knot in the support of the B-spline. + * In other words it returns the lower bound of the support. * * @param[in] ix DiscreteElement identifying the B-spline. * @return Coordinate of the knot. @@ -202,7 +228,11 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase return ddc::coordinate(ddc::DiscreteElement(ix.uid())); } - /** @brief Returns the coordinate of the last support knot associated to a discrete_element identifying a B-spline. + /** @brief Returns the coordinate of the last support knot associated to a DiscreteElement identifying a B-spline. + * + * Each B-spline has a support defined over (degree+2) knots. For a B-spline identified by the + * provided DiscreteElement, this function returns the last knot in the support of the B-spline. + * In other words it returns the upper bound of the support. * * @param[in] ix DiscreteElement identifying the B-spline. * @return Coordinate of the knot. @@ -213,7 +243,10 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase return ddc::coordinate(ddc::DiscreteElement(ix.uid() + degree() + 1)); } - /** @brief Returns the coordinate of the \f$n\f$-th knot associated to a DiscreteElement identifying a B-spline. + /** @brief Returns the coordinate of the first knot in the support of the identified B-spline. + * + * Each B-spline has a support defined over (degree+2) knots. For a B-spline identified by the + * provided DiscreteElement, this function returns the (n+1)-th knot in the support of the B-spline. * * @param[in] ix DiscreteElement identifying the B-spline. * @param[in] n Integer indexing a knot in the support of the B-spline. diff --git a/include/ddc/kernels/splines/bsplines_uniform.hpp b/include/ddc/kernels/splines/bsplines_uniform.hpp index 2cf34afad..692667d12 100644 --- a/include/ddc/kernels/splines/bsplines_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_uniform.hpp @@ -31,7 +31,7 @@ struct UniformBSplinesBase /** * The type of a uniform B-splines 1D basis. * - * @tparam Tag The tag identifying the continuous dimension which supports the building of the B-splines. + * @tparam Tag The tag identifying the continuous dimension on which the support of the B-spline functions are defined. * @tparam D The degree of the B-splines. */ template @@ -40,7 +40,7 @@ class UniformBSplines : detail::UniformBSplinesBase static_assert(D > 0, "Parameter `D` must be positive"); public: - /// @brief The tag identifying the continuous dimension which supports the building of the B-splines. + /// @brief The tag identifying the continuous dimension on which the support of the B-splines are defined. using tag_type = Tag; /// @brief The discrete dimension representing B-splines. @@ -87,7 +87,7 @@ class UniformBSplines : detail::UniformBSplinesBase /// @brief The type of the discrete dimension representing the B-splines. using discrete_dimension_type = UniformBSplines; - /// @brief The type of a discrete domain identifying the B-splines. + /// @brief The type of a discrete domain whose elements identify the B-splines. using discrete_domain_type = DiscreteDomain; /// @brief The type of a discrete element identifying a B-spline. @@ -137,12 +137,17 @@ class UniformBSplines : detail::UniformBSplinesBase /// @brief Move-assigns Impl& operator=(Impl&& x) = default; - /** @brief Evaluates B-splines at a given coordinate + /** @brief Evaluates non-zero B-splines at a given coordinate. * - * The values are computed for every B-splines at the given coordinate x. A spline approximation at coordinate x is a linear combination of those B-splines evaluations weigthed with splines coefficients of the spline-transformed initial discrete function. - * @param[out] values The values of the B-splines evaluated at coordinate x. It has to be a (1+degree) 1D mdspan. + * The values are computed for every B-spline with support at the given coordinate x. There are only (degree+1) + * B-splines which are non-zero at any given point. It is these B-splines which are evaluated. + * This can be useful to calculate a spline approximation of a function. A spline approximation at coordinate x + * is a linear combination of these B-spline evaluations weighted with spline coefficients of the spline-transformed + * initial discrete function. + * + * @param[out] values The values of the B-splines evaluated at coordinate x. It has to be a 1D mdspan with (degree+1) elements. * @param[in] x The coordinate where B-splines are evaluated. - * @return TODO + * @return The index of the first B-spline which is evaluated. */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_basis(DSpan1D values, ddc::Coordinate const& x) const @@ -151,23 +156,33 @@ class UniformBSplines : detail::UniformBSplinesBase return eval_basis(values, x, degree()); } - /** @brief Evaluates B-splines derivatives at a given coordinate + /** @brief Evaluates non-zero B-splines derivatives at a given coordinate + * + * The derivatives are computed for every B-splines with support at the given coordinate x. There are only (degree+1) + * B-splines which are non-zero at any given point. It is these B-splines which are derivated. + * A spline approximation of a derivative at coordinate x is a linear + * combination of those B-splines derivatives weigthed with splines coefficients of the spline-transformed + * initial discrete function. * - * The derivatives are computed for every B-splines at the given coordinate x. A spline approximation of a derivative at coordinate x is a linear combination of those B-splines derivatives weigthed with splines coefficients of the spline-transformed initial discrete function. - * @param[out] derivs The derivatives of the B-splines evaluated at coordinate x. It has to be a (1+degree) 1D mdspan. + * @param[out] derivs The derivatives of the B-splines evaluated at coordinate x. It has to be a 1D mdspan with (degree+1) elements. * @param[in] x The coordinate where B-splines derivatives are evaluated. - * @return TODO + * @return The index of the first B-spline which is evaluated. */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_deriv(DSpan1D derivs, ddc::Coordinate const& x) const; - /** @brief Evaluates B-splines values and \f$n\f$ derivatives at a given coordinate + /** @brief Evaluates non-zero B-splines values and \f$n\f$ derivatives at a given coordinate + * + * The values and derivatives are computed for every B-splines with support at the given coordinate x. There are only (degree+1) + * B-splines which are non-zero at any given point. It is these B-splines which are derivated. + * A spline approximation of a derivative at coordinate x is a linear + * combination of those B-splines derivatives weigthed with splines coefficients of the spline-transformed + * initial discrete function. * - * The values and derivatives are computed for every B-splines at the given coordinate x. - * @param[out] derivs The values and n derivatives of the B-splines evaluated at coordinate x. It has to be a (1+degree)*(1+n) 2D mdspan. - * @param[in] x The coordinates where B-splines derivatives are evaluated. + * @param[out] derivs The values and \f$n\f$ derivatives of the B-splines evaluated at coordinate x. It has to be a 2D mdspan with (degree+1)*(n+1) elements. + * @param[in] x The coordinate where B-splines derivatives are evaluated. * @param[in] n The number of derivatives to evaluate (in addition to the B-splines values themselves). - * @return TODO + * @return The index of the first B-spline which is evaluated. */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_basis_and_n_derivs( ddc::DSpan2D derivs, @@ -176,7 +191,9 @@ class UniformBSplines : detail::UniformBSplinesBase /** @brief Compute the integrals of the B-splines. * - * @param[out] int_vals The values of the integrals. It has to be a (1+nbasis) 1D mdspan. + * The integral of each of the B-splines over their support within the domain on which this basis was defined. + * + * @param[out] int_vals The values of the integrals. It has to be a (nbasis) 1D mdspan. * @return The values of the integrals. */ template @@ -184,7 +201,12 @@ class UniformBSplines : detail::UniformBSplinesBase integrals( ddc::ChunkSpan int_vals) const; - /** @brief Returns the coordinate of the knot corresponding to the given index for a B-spline. + /** @brief Returns the coordinate of the knot corresponding to the given index. + * + * Returns the coordinate of the knot corresponding to the given index for a B-spline. The domain + * over which the B-splines are defined is comprised of ncells+1 knots however there are a total of + * ncells+1+2*degree knots. The additional knots which control the shape of the B-splines near the + * boundary are added before and after the break points. The knot index is therefore in the interval [-degree, ncells+degree] * * @param[in] idx Integer identifying index of the knot. * @return Coordinate of the knot. @@ -195,6 +217,10 @@ class UniformBSplines : detail::UniformBSplinesBase } /** @brief Returns the coordinate of the first support knot associated to a DiscreteElement identifying a B-spline. + * + * Each B-spline has a support defined over (degree+2) knots. For a B-spline identified by the + * provided DiscreteElement, this function returns the first knot in the support of the B-spline. + * In other words it returns the lower bound of the support. * * @param[in] ix DiscreteElement identifying the B-spline. * @return Coordinate of the knot. @@ -205,6 +231,10 @@ class UniformBSplines : detail::UniformBSplinesBase } /** @brief Returns the coordinate of the last support knot associated to a DiscreteElement identifying a B-spline. + * + * Each B-spline has a support defined over (degree+2) knots. For a B-spline identified by the + * provided DiscreteElement, this function returns the last knot in the support of the B-spline. + * In other words it returns the upper bound of the support. * * @param[in] ix DiscreteElement identifying the B-spline. * @return Coordinate of the knot. @@ -214,7 +244,10 @@ class UniformBSplines : detail::UniformBSplinesBase return get_knot(ix.uid() + 1); } - /** @brief Returns the coordinate of the \f$n\f$-th knot associated to a DiscreteElement identifying a B-spline. + /** @brief Returns the coordinate of the first knot in the support of the identified B-spline. + * + * Each B-spline has a support defined over (degree+2) knots. For a B-spline identified by the + * provided DiscreteElement, this function returns the (n+1)-th knot in the support of the B-spline. * * @param[in] ix DiscreteElement identifying the B-spline. * @param[in] n Integer indexing a knot in the support of the B-spline. From 0589694d56089638578034a187d616a85c22cf50 Mon Sep 17 00:00:00 2001 From: Baptiste Legouix Date: Mon, 22 Apr 2024 09:34:04 +0200 Subject: [PATCH 035/189] Update include/ddc/kernels/splines/bsplines_non_uniform.hpp Co-authored-by: Thomas Padioleau --- include/ddc/kernels/splines/bsplines_non_uniform.hpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index 34b19f826..9d0db9074 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -59,7 +59,7 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase } /// @brief Indicates if the B-splines are radial or not (should be deprecated soon because this concept is not in the scope of DDC). - static constexpr bool is_radial() noexcept + [[deprecated]] static constexpr bool is_radial() noexcept { return false; } From ffe161efcd9f2b262398fce4dc27eb6d249ea3ce Mon Sep 17 00:00:00 2001 From: blegouix Date: Mon, 22 Apr 2024 10:13:10 +0200 Subject: [PATCH 036/189] wip --- include/ddc/kernels/splines/bsplines_non_uniform.hpp | 2 +- include/ddc/kernels/splines/bsplines_uniform.hpp | 6 +++--- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index 34b19f826..05a4c8872 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -200,7 +200,7 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase /** @brief Returns the coordinate of the knot corresponding to the given index. * - * Returns the coordinate of the knot corresponding to the given index for a B-spline. The domain + * Returns the coordinate of the knot corresponding to the given index. The domain * over which the B-splines are defined is comprised of ncells+1 knots however there are a total of * ncells+1+2*degree knots. The additional knots which control the shape of the B-splines near the * boundary are added before and after the break points. The knot index is therefore in the interval [-degree, ncells+degree] diff --git a/include/ddc/kernels/splines/bsplines_uniform.hpp b/include/ddc/kernels/splines/bsplines_uniform.hpp index 692667d12..cfd499804 100644 --- a/include/ddc/kernels/splines/bsplines_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_uniform.hpp @@ -203,15 +203,15 @@ class UniformBSplines : detail::UniformBSplinesBase /** @brief Returns the coordinate of the knot corresponding to the given index. * - * Returns the coordinate of the knot corresponding to the given index for a B-spline. The domain + * Returns the coordinate of the knot corresponding to the given index. The domain * over which the B-splines are defined is comprised of ncells+1 knots however there are a total of * ncells+1+2*degree knots. The additional knots which control the shape of the B-splines near the * boundary are added before and after the break points. The knot index is therefore in the interval [-degree, ncells+degree] * - * @param[in] idx Integer identifying index of the knot. + * @param[in] knot_idx Integer identifying index of the knot. * @return Coordinate of the knot. */ - KOKKOS_INLINE_FUNCTION ddc::Coordinate get_knot(int idx) const noexcept + KOKKOS_INLINE_FUNCTION ddc::Coordinate get_knot(int knot_idx) const noexcept { return ddc::Coordinate(rmin() + idx * ddc::step()); } From f853bca264c4072c0d03b78d72b8238316a71730 Mon Sep 17 00:00:00 2001 From: blegouix Date: Mon, 22 Apr 2024 11:32:45 +0200 Subject: [PATCH 037/189] reviews --- .../kernels/splines/bsplines_non_uniform.hpp | 57 ++++++++++++------- .../ddc/kernels/splines/bsplines_uniform.hpp | 49 ++++++++++------ 2 files changed, 67 insertions(+), 39 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index 79e78bdf8..dae5c9b88 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -59,7 +59,7 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase } /// @brief Indicates if the B-splines are radial or not (should be deprecated soon because this concept is not in the scope of DDC). - [[deprecated]] static constexpr bool is_radial() noexcept + [[deprecated]] static constexpr bool is_radial() noexcept { return false; } @@ -70,7 +70,11 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase return false; } - /// @brief Impl TODO + /** @brief Impl Storage class of the static attributes of the discrete dimension. + * + * @tparam DDim The name of the discrete dimension. + * @tparam MemorySpace The Kokkos memory space where the attributes are being stored. + */ template class Impl { @@ -190,7 +194,7 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase * * The integral of each of the B-splines over their support within the domain on which this basis was defined. * - * @param[out] int_vals The values of the integrals. It has to be a (nbasis) 1D mdspan. + * @param[out] int_vals The values of the integrals. It has to be a 1D mdspan of size (nbasis). * @return The values of the integrals. */ template @@ -259,74 +263,85 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase return ddc::coordinate(ddc::DiscreteElement(ix.uid() + n)); } - /** @brief Returns the coordinate of the lower boundary knot. + /** @brief Returns the coordinate of the lower bound of the domain on which the B-splines are defined. * - * @return Coordinate of the lower boundary knot. + * @return Coordinate of the lower bound of the domain. */ KOKKOS_INLINE_FUNCTION ddc::Coordinate rmin() const noexcept { return get_knot(0); } - /** @brief Returns the coordinate of the upper boundary knot. + /** @brief Returns the coordinate of the upper bound of the domain on which the B-splines are defined. * - * @return Coordinate of the upper boundary knot. + * @return Coordinate of the upper bound of the domain. */ KOKKOS_INLINE_FUNCTION ddc::Coordinate rmax() const noexcept { return get_knot(ncells()); } - /** @brief Returns the length of the domain supporting knots. + /** @brief Returns the length of the domain. * - * @return The length of the domain supporting knots. + * @return The length of the domain. */ KOKKOS_INLINE_FUNCTION double length() const noexcept { return rmax() - rmin(); } - /** @brief TODO + /** @brief Returns the number of elements necessary to construct a spline representation of a function. + * + * For a non-periodic domain the number of elements necessary to construct a spline representation of a function + * is equal to the number of basis functions. However in the periodic case it additionally includes degree additional elements + * which allow the first B-splines to be evaluated close to rmax (where they also appear due to the periodicity). * - * @return TODO. + * @return The number of elements necessary to construct a spline representation of a function. */ KOKKOS_INLINE_FUNCTION std::size_t size() const noexcept { return degree() + ncells(); } - /** @brief Returns the discrete domain including ghost bsplines + /** @brief Returns the discrete domain including eventual additionnal bsplines in the periodic case. See size(). * - * @return The discrete domain including ghost bsplines. + * @return The discrete domain including eventual additionnal bsplines. */ KOKKOS_INLINE_FUNCTION discrete_domain_type full_domain() const { return discrete_domain_type(discrete_element_type(0), discrete_vector_type(size())); } - /** @brief TODO + /** @brief The number of break points + * + * The number of break points or cell boundaries. * - * @return TODO + * @return The number of break points */ KOKKOS_INLINE_FUNCTION std::size_t npoints() const noexcept { return m_nknots - 2 * degree(); } - /** @brief TODO + /** @brief Returns the number of basis functions. * - * @return TODO + * The number of functions in the spline basis. + * + * @return The number of basis functions. */ KOKKOS_INLINE_FUNCTION std::size_t nbasis() const noexcept { return ncells() + !is_periodic() * degree(); } - /** @brief TODO + /** @brief Returns the number of cells over which the B-splines are defined. + * + * The number of cells over which the B-splines and any spline representation are defined. + * In other words the number of polynomials that comprise a spline representation on the domain where the basis is defined. * - * @return TODO + * @return The number of cells over which the B-splines are defined. */ - KOKKOS_INLINE_FUNCTION std::size_t ncells() const noexcept + KOKKOS_INLINE_FUNCTIO std::size_t ncells() const noexcept { return npoints() - 1; } @@ -342,7 +357,7 @@ struct is_non_uniform_bsplines : public std::is_base_of class Impl { @@ -193,7 +197,7 @@ class UniformBSplines : detail::UniformBSplinesBase * * The integral of each of the B-splines over their support within the domain on which this basis was defined. * - * @param[out] int_vals The values of the integrals. It has to be a (nbasis) 1D mdspan. + * @param[out] int_vals The values of the integrals. It has to be a 1D mdspan of size (nbasis). * @return The values of the integrals. */ template @@ -259,63 +263,72 @@ class UniformBSplines : detail::UniformBSplinesBase return get_knot(ix.uid() + n - degree()); } - /** @brief Returns the coordinate of the lower boundary knot. + /** @brief Returns the coordinate of the lower bound of the domain on which the B-splines are defined. * - * @return Coordinate of the lower boundary knot. + * @return Coordinate of the lower bound of the domain. */ KOKKOS_INLINE_FUNCTION ddc::Coordinate rmin() const noexcept { return ddc::coordinate(m_domain.front()); } - /** @brief Returns the coordinate of the upper boundary knot. + /** @brief Returns the coordinate of the upper bound of the domain on which the B-splines are defined. * - * @return Coordinate of the upper boundary knot. + * @return Coordinate of the upper bound of the domain. */ KOKKOS_INLINE_FUNCTION ddc::Coordinate rmax() const noexcept { return ddc::coordinate(m_domain.back()); } - /** @brief Returns the length of the domain supporting knots. + /** @brief Returns the length of the domain. * - * @return The length of the domain supporting knots. + * @return The length of the domain. */ KOKKOS_INLINE_FUNCTION double length() const noexcept { return rmax() - rmin(); } - /** @brief TODO (number of knots ?). + /** @brief Returns the number of elements necessary to construct a spline representation of a function. * - * @return TODO. + * For a non-periodic domain the number of elements necessary to construct a spline representation of a function + * is equal to the number of basis functions. However in the periodic case it additionally includes degree additional elements + * which allow the first B-splines to be evaluated close to rmax (where they also appear due to the periodicity). + * + * @return The number of elements necessary to construct a spline representation of a function. */ KOKKOS_INLINE_FUNCTION std::size_t size() const noexcept { return degree() + ncells(); } - /** @brief Returns the discrete domain including ghost bsplines + /** @brief Returns the discrete domain including eventual additionnal bsplines in the periodic case. See size(). * - * @return The discrete domain including ghost bsplines. + * @return The discrete domain including eventual additionnal bsplines. */ KOKKOS_INLINE_FUNCTION discrete_domain_type full_domain() const { return discrete_domain_type(discrete_element_type(0), discrete_vector_type(size())); } - /** @brief TODO + /** @brief Returns the number of basis functions. + * + * The number of functions in the spline basis. * - * @return TODO + * @return The number of basis functions. */ KOKKOS_INLINE_FUNCTION std::size_t nbasis() const noexcept { return ncells() + !is_periodic() * degree(); } - /** @brief TODO + /** @brief Returns the number of cells over which the B-splines are defined. + * + * The number of cells over which the B-splines and any spline representation are defined. + * In other words the number of polynomials that comprise a spline representation on the domain where the basis is defined. * - * @return TODO + * @return The number of cells over which the B-splines are defined. */ KOKKOS_INLINE_FUNCTION std::size_t ncells() const noexcept { @@ -344,7 +357,7 @@ struct is_uniform_bsplines : public std::is_base_of Date: Mon, 22 Apr 2024 12:32:16 +0200 Subject: [PATCH 038/189] typo --- include/ddc/kernels/splines/bsplines_non_uniform.hpp | 2 +- include/ddc/kernels/splines/bsplines_uniform.hpp | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index dae5c9b88..1173e42bc 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -247,7 +247,7 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase return ddc::coordinate(ddc::DiscreteElement(ix.uid() + degree() + 1)); } - /** @brief Returns the coordinate of the first knot in the support of the identified B-spline. + /** @brief Returns the coordinate of the (n+1)-th knot in the support of the identified B-spline. * * Each B-spline has a support defined over (degree+2) knots. For a B-spline identified by the * provided DiscreteElement, this function returns the (n+1)-th knot in the support of the B-spline. diff --git a/include/ddc/kernels/splines/bsplines_uniform.hpp b/include/ddc/kernels/splines/bsplines_uniform.hpp index 5ff0e4dc9..13d4726f4 100644 --- a/include/ddc/kernels/splines/bsplines_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_uniform.hpp @@ -248,7 +248,7 @@ class UniformBSplines : detail::UniformBSplinesBase return get_knot(ix.uid() + 1); } - /** @brief Returns the coordinate of the first knot in the support of the identified B-spline. + /** @brief Returns the coordinate of the (n+1)-th knot in the support of the identified B-spline. * * Each B-spline has a support defined over (degree+2) knots. For a B-spline identified by the * provided DiscreteElement, this function returns the (n+1)-th knot in the support of the B-spline. From 65c221e1442ecddaeaab7beb05f0e57096104773 Mon Sep 17 00:00:00 2001 From: blegouix Date: Mon, 22 Apr 2024 12:34:02 +0200 Subject: [PATCH 039/189] fix --- include/ddc/kernels/splines/bsplines_non_uniform.hpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index 1173e42bc..13a0ecb17 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -341,7 +341,7 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase * * @return The number of cells over which the B-splines are defined. */ - KOKKOS_INLINE_FUNCTIO std::size_t ncells() const noexcept + KOKKOS_INLINE_FUNCTION std::size_t ncells() const noexcept { return npoints() - 1; } From 49b9b01a01751445c260bb219c9c84f62031c1fc Mon Sep 17 00:00:00 2001 From: blegouix Date: Mon, 22 Apr 2024 12:38:04 +0200 Subject: [PATCH 040/189] minor --- include/ddc/kernels/splines/bsplines_non_uniform.hpp | 6 +++--- include/ddc/kernels/splines/bsplines_uniform.hpp | 6 +++--- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index 13a0ecb17..e6022fce0 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -92,13 +92,13 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase /// @brief The type of the discrete dimension representing the B-splines. using discrete_dimension_type = NonUniformBSplines; - /// @brief The type of a discrete domain whose elements identify the B-splines. + /// @brief The type of a DiscreteDomain whose elements identify the B-splines. using discrete_domain_type = DiscreteDomain; - /// @brief The type of a discrete element identifying a B-spline. + /// @brief The type of a DiscreteElement identifying a B-spline. using discrete_element_type = DiscreteElement; - /// @brief The type of a discrete vector representing an "index displacement" between two B-splines. + /// @brief The type of a DiscreteVector representing an "index displacement" between two B-splines. using discrete_vector_type = DiscreteVector; Impl() = default; diff --git a/include/ddc/kernels/splines/bsplines_uniform.hpp b/include/ddc/kernels/splines/bsplines_uniform.hpp index 13d4726f4..4194fc377 100644 --- a/include/ddc/kernels/splines/bsplines_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_uniform.hpp @@ -91,13 +91,13 @@ class UniformBSplines : detail::UniformBSplinesBase /// @brief The type of the discrete dimension representing the B-splines. using discrete_dimension_type = UniformBSplines; - /// @brief The type of a discrete domain whose elements identify the B-splines. + /// @brief The type of a DiscreteDomain whose elements identify the B-splines. using discrete_domain_type = DiscreteDomain; - /// @brief The type of a discrete element identifying a B-spline. + /// @brief The type of a DiscreteElement identifying a B-spline. using discrete_element_type = DiscreteElement; - /// @brief The type of a discrete vector representing an "index displacement" between two B-splines. + /// @brief The type of a DiscreteVector representing an "index displacement" between two B-splines. using discrete_vector_type = DiscreteVector; Impl() = default; From 195dc501fa1873c07e9eaa7e237af31301fd8654 Mon Sep 17 00:00:00 2001 From: blegouix Date: Mon, 22 Apr 2024 12:50:13 +0200 Subject: [PATCH 041/189] more details on uniformity --- include/ddc/kernels/splines/bsplines_non_uniform.hpp | 3 +++ include/ddc/kernels/splines/bsplines_uniform.hpp | 2 ++ 2 files changed, 5 insertions(+) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index e6022fce0..3a740809f 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -31,6 +31,9 @@ struct NonUniformBSplinesBase /** * The type of a non-uniform B-splines 1D basis. * + * Knots for non-uniform B-splines are non-uniformly distributed (no assumption is made on the uniformity of their distribution, + * the associated discrete dimension is a NonUniformPointSampling). + * * @tparam Tag The tag identifying the continuous dimension on which the support of the B-spline functions are defined. * @tparam D The degree of the B-splines. */ diff --git a/include/ddc/kernels/splines/bsplines_uniform.hpp b/include/ddc/kernels/splines/bsplines_uniform.hpp index 4194fc377..6c47b930e 100644 --- a/include/ddc/kernels/splines/bsplines_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_uniform.hpp @@ -31,6 +31,8 @@ struct UniformBSplinesBase /** * The type of a uniform B-splines 1D basis. * + * Knots for non-uniform B-splines basis are non-uniformly distributed (no assumption is made on the uniformity of their distribution). + * * @tparam Tag The tag identifying the continuous dimension on which the support of the B-spline functions are defined. * @tparam D The degree of the B-splines. */ From bae41cc7d22ed5464a816d64484655ad14d2bd10 Mon Sep 17 00:00:00 2001 From: blegouix Date: Mon, 22 Apr 2024 13:13:33 +0200 Subject: [PATCH 042/189] non-uniform constructors --- .../kernels/splines/bsplines_non_uniform.hpp | 17 ++++++++++++++--- 1 file changed, 14 insertions(+), 3 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index 3a740809f..5d86051d3 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -106,19 +106,30 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase Impl() = default; - /// @brief Construct a `Impl` using a brace-list, i.e. `Impl bsplines({0., 1.})` + /** @brief Constructs an Impl using a brace-list, i.e. `Impl bsplines({0., 1.})` + * + * The brace-list is usually the iterable list of knots. However, only the first and last + * indexes of the elements of the lists are effectively used by the constructor to build the Impl. + */ explicit Impl(std::initializer_list> breaks) : Impl(breaks.begin(), breaks.end()) { } - /// @brief Construct a `Impl` using a C++20 "common range". + /** @brief Constructs an Impl using a std::vector. + * + * The std::vector is usually the iterable list of knots. However, only the first and last + * indexes of the elements of the lists are effectively used by the constructor to build the Impl. + */ explicit Impl(std::vector> const& breaks) : Impl(breaks.begin(), breaks.end()) { } - /// @brief Construct a `Impl` using a pair of iterators. + /** @brief Construct a `Impl` using a pair of iterators. + * + * The (lower and upper) iterators are used to build the DiscreteDomain indexing the B-splines. + */ template Impl(RandomIt breaks_begin, RandomIt breaks_end); From e702a5be835d9558fe5cc27ee3d1985bfd36d125 Mon Sep 17 00:00:00 2001 From: blegouix Date: Mon, 22 Apr 2024 13:17:06 +0200 Subject: [PATCH 043/189] minor --- include/ddc/kernels/splines/bsplines_non_uniform.hpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index 5d86051d3..ab3d11362 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -126,7 +126,7 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase { } - /** @brief Construct a `Impl` using a pair of iterators. + /** @brief Constructs a Impl using a pair of iterators. * * The (lower and upper) iterators are used to build the DiscreteDomain indexing the B-splines. */ From f31ab4a8d8c3ebf1e710fb5f515f89a46c73e1ff Mon Sep 17 00:00:00 2001 From: blegouix Date: Mon, 22 Apr 2024 13:53:07 +0200 Subject: [PATCH 044/189] non_uniform constructors again --- include/ddc/kernels/splines/bsplines_non_uniform.hpp | 11 ++++++----- 1 file changed, 6 insertions(+), 5 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index ab3d11362..cdde6409c 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -108,8 +108,8 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase /** @brief Constructs an Impl using a brace-list, i.e. `Impl bsplines({0., 1.})` * - * The brace-list is usually the iterable list of knots. However, only the first and last - * indexes of the elements of the lists are effectively used by the constructor to build the Impl. + * The brace-list is the list of break points. It is used to build the DiscreteDomain indexing + * the knots and iterated over to build the knots coordinates list and initialize the associated DiscreteSpace. */ explicit Impl(std::initializer_list> breaks) : Impl(breaks.begin(), breaks.end()) @@ -118,8 +118,8 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase /** @brief Constructs an Impl using a std::vector. * - * The std::vector is usually the iterable list of knots. However, only the first and last - * indexes of the elements of the lists are effectively used by the constructor to build the Impl. + * The std::vector is the list of break points. It is used to build the DiscreteDomain indexing + * the knots and iterated over to build the knots coordinates list and initialize the associated DiscreteSpace. */ explicit Impl(std::vector> const& breaks) : Impl(breaks.begin(), breaks.end()) @@ -128,7 +128,8 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase /** @brief Constructs a Impl using a pair of iterators. * - * The (lower and upper) iterators are used to build the DiscreteDomain indexing the B-splines. + * The iterators are used to build the DiscreteDomain indexing the knots, build the knots list + * and initialize the associated DiscreteSpace. */ template Impl(RandomIt breaks_begin, RandomIt breaks_end); From f180f4d9bf3db6952e5d769362c78c5268f59960 Mon Sep 17 00:00:00 2001 From: blegouix Date: Mon, 22 Apr 2024 15:00:43 +0200 Subject: [PATCH 045/189] wip --- .../ddc/kernels/splines/spline_builder.hpp | 4 ++- .../ddc/kernels/splines/spline_builder_2d.hpp | 27 +++++++++++++++++++ 2 files changed, 30 insertions(+), 1 deletion(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index b2b112d59..4e0859b7f 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -23,10 +23,11 @@ enum class SplineSolver { GINKGO }; * @brief An helper giving the uniform/non_uniform status of a spline interpolation mesh according to its attributes. * * An helper giving the uniform/non_uniform status of a spline interpolation mesh according to its attributes. + * * @param is_uniform A boolean giving the presumed status before considering boundary conditions. * @param BcXmin The lower boundary condition. * @param BcXmax The upper boundary condition. - * @param int The degree of the spline. + * @param degree The degree of the spline. */ constexpr bool is_spline_interpolation_mesh_uniform( bool const is_uniform, @@ -214,6 +215,7 @@ class SplineBuilder * * @param batched_interpolation_domain The domain on which are defined the interpolation points. * @param cols_per_chunk An hyperparameter used by the slicer (internal to the solver) to define the size of a chunk of right-and-sides of the linear problem to be computed in parallel. + * @param preconditionner_max_block_size An hyperparameter used by the slicer (internal to the solver) to define the size of a block used by Block-Jacobi preconditionner. */ explicit SplineBuilder( batched_interpolation_domain_type const& batched_interpolation_domain, diff --git a/include/ddc/kernels/splines/spline_builder_2d.hpp b/include/ddc/kernels/splines/spline_builder_2d.hpp index 872bf2956..ae3cfc178 100644 --- a/include/ddc/kernels/splines/spline_builder_2d.hpp +++ b/include/ddc/kernels/splines/spline_builder_2d.hpp @@ -120,25 +120,45 @@ class SplineBuilder2D using interpolation_domain_type = ddc::DiscreteDomain; + /** + * @brief The type of the whole domain representing interpolation points. + */ using batched_interpolation_domain_type = ddc::DiscreteDomain; + /** + * @brief The type of the batch domain (obtained by removing dimensions of interests from whole space). + */ using batch_domain_type = ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq>>; + /** + * @brief The type of the whole spline domain (cartesian product of 2D spline domain and batch domain) preserving the underlying memory layout (order of dimensions). + */ using batched_spline_domain_type = ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq, ddc::detail::TypeSeq>>; + /** + * @brief The type of the whole Derivs domain (cartesian product of the 1D Deriv domain and the associated batch domain) in the first dimension used by the class, preserving the underlying memory layout (order of dimensions). + */ using batched_derivs_domain_type1 = typename builder_type1::batched_derivs_domain_type; + + /** + * @brief The type of the whole Derivs domain (cartesian product of the 1D Deriv domain and the associated batch domain) in the second dimension used by the class, preserving the underlying memory layout (order of dimensions). + */ using batched_derivs_domain_type2 = ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq, ddc::detail::TypeSeq>>; + + /** + * @brief The type of the whole Derivs domain (cartesian product of the 2D Deriv domain and the batch domain) in the second dimension used by the class, preserving the underlying memory layout (order of dimensions). + */ using batched_derivs_domain_type = ddc::detail::convert_type_seq_to_discrete_domain, @@ -251,6 +271,13 @@ class SplineBuilder2D ddc::discrete_space().full_domain()); } + /** + * @brief Get the whole domain on which spline coefficients are defined, preserving memory layout. + * + * Get the whole domain on which spline coefficients will be computed, preserving memory layout (order of dimensions). + * + * @return The domain for the spline coefficients. + */ batched_spline_domain_type batched_spline_domain() const noexcept { return ddc::replace_dim_of( From 1484581e7369c4fa4ac707090f0b23806204bcd1 Mon Sep 17 00:00:00 2001 From: blegouix Date: Mon, 22 Apr 2024 16:20:14 +0200 Subject: [PATCH 046/189] wip on CI --- .../kernels/splines/bsplines_non_uniform.hpp | 45 +++++++++++++++---- .../ddc/kernels/splines/bsplines_uniform.hpp | 45 +++++++++++++++---- 2 files changed, 72 insertions(+), 18 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index cdde6409c..b38fb0ca7 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -49,25 +49,37 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase /// @brief The discrete dimension identifying B-splines. using discrete_dimension_type = NonUniformBSplines; - /// @brief The degree of B-splines. + /** @brief The degree of B-splines. + * + * @return The degree. + */ static constexpr std::size_t degree() noexcept { return D; } - /// @brief Indicates if the B-splines are periodic or not. + /** @brief Indicates if the B-splines are periodic or not. + * + * @return A boolean indicating if the B-splines are periodic or not. + */ static constexpr bool is_periodic() noexcept { return Tag::PERIODIC; } - /// @brief Indicates if the B-splines are radial or not (should be deprecated soon because this concept is not in the scope of DDC). + /** @brief Indicates if the B-splines are radial or not (should be deprecated soon because this concept is not in the scope of DDC). + * + * @return A boolean indicating if the dimension is radial or not. + */ [[deprecated]] static constexpr bool is_radial() noexcept { return false; } - /// @brief Indicates if the B-splines are uniform or not (this is not the case here). + /** @brief Indicates if the B-splines are uniform or not (this is not the case here). + * + * @return A boolean indicating if the B-splines are uniform or not. + */ static constexpr bool is_uniform() noexcept { return false; @@ -134,7 +146,10 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase template Impl(RandomIt breaks_begin, RandomIt breaks_end); - /// @brief Copy-constructs from another Impl with different Kokkos memory space + /** @brief Copy-constructs from another Impl with different Kokkos memory space + * + * @param A reference to the other Impl + */ template explicit Impl(Impl const& impl) : m_domain(impl.m_domain) @@ -142,19 +157,31 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase { } - /// @brief Copy-constructs + /** @brief Copy-constructs + * + * @param A reference to another Impl + */ Impl(Impl const& x) = default; - /// @brief Move-constructs + /** @brief Move-constructs + * + * @param An rvalue to another Impl + */ Impl(Impl&& x) = default; /// @brief Destructs ~Impl() = default; - /// @brief Copy-assigns + /** @brief Copy-assigns + * + * @param A reference to another Impl + */ Impl& operator=(Impl const& x) = default; - /// @brief Move-assigns + /** @brief Move-assigns + * + * @param An rvalue to another Impl + */ Impl& operator=(Impl&& x) = default; /** @brief Evaluates non-zero B-splines at a given coordinate. diff --git a/include/ddc/kernels/splines/bsplines_uniform.hpp b/include/ddc/kernels/splines/bsplines_uniform.hpp index 6c47b930e..f9ab5ac28 100644 --- a/include/ddc/kernels/splines/bsplines_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_uniform.hpp @@ -48,25 +48,37 @@ class UniformBSplines : detail::UniformBSplinesBase /// @brief The discrete dimension representing B-splines. using discrete_dimension_type = UniformBSplines; - /// @brief The degree of B-splines. + /** @brief The degree of B-splines. + * + * @return The degree. + */ static constexpr std::size_t degree() noexcept { return D; } - /// @brief Indicates if the B-splines are periodic or not. + /** @brief Indicates if the B-splines are periodic or not. + * + * @return A boolean indicating if the B-splines are periodic or not. + */ static constexpr bool is_periodic() noexcept { return Tag::PERIODIC; } - /// @brief Indicates if the B-splines are radial or not (should be deprecated soon because this concept is not in the scope of DDC). + /** @brief Indicates if the B-splines are radial or not (should be deprecated soon because this concept is not in the scope of DDC). + * + * @return A boolean indicating if the dimension is radial or not. + */ [[deprecated]] static constexpr bool is_radial() noexcept { return false; } - /// @brief Indicates if the B-splines are uniform or not (this is the case here). + /** @brief Indicates if the B-splines are uniform or not (this is the case here). + * + * @return A boolean indicating if the B-splines are uniform or not. + */ static constexpr bool is_uniform() noexcept { return true; @@ -122,25 +134,40 @@ class UniformBSplines : detail::UniformBSplinesBase mesh_type>(rmin, rmax, ddc::DiscreteVector(ncells + 1))); } - /// @brief Copy-constructs from another Impl with different Kokkos memory space + /** @brief Copy-constructs from another Impl with different Kokkos memory space + * + * @param A reference to the other Impl + */ template explicit Impl(Impl const& impl) : m_domain(impl.m_domain) { } - /// @brief Copy-constructs + /** @brief Copy-constructs + * + * @param A reference to another Impl + */ Impl(Impl const& x) = default; - /// @brief Move-constructs + /** @brief Move-constructs + * + * @param An rvalue to another Impl + */ Impl(Impl&& x) = default; /// @brief Destructs ~Impl() = default; - /// @brief Copy-assigns + /** @brief Copy-assigns + * + * @param A reference to another Impl + */ Impl& operator=(Impl const& x) = default; - /// @brief Move-assigns + /** @brief Move-assigns + * + * @param An rvalue to another Impl + */ Impl& operator=(Impl&& x) = default; /** @brief Evaluates non-zero B-splines at a given coordinate. From 792b7f1ca1daf3ff6f5761b15ecb9d69a066441a Mon Sep 17 00:00:00 2001 From: blegouix Date: Mon, 22 Apr 2024 16:34:46 +0200 Subject: [PATCH 047/189] wip on CI --- .../kernels/splines/bsplines_non_uniform.hpp | 17 ++++++++++++----- .../ddc/kernels/splines/bsplines_uniform.hpp | 10 +++++----- 2 files changed, 17 insertions(+), 10 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index d8b114930..7139297c9 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -113,6 +113,8 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase * * The brace-list is the list of break points. It is used to build the DiscreteDomain indexing * the knots and iterated over to build the knots coordinates list and initialize the associated DiscreteSpace. + * + * @param breaks The std::initializer_list of the coordinates of break points. */ explicit Impl(std::initializer_list> breaks) : Impl(breaks.begin(), breaks.end()) @@ -123,6 +125,8 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase * * The std::vector is the list of break points. It is used to build the DiscreteDomain indexing * the knots and iterated over to build the knots coordinates list and initialize the associated DiscreteSpace. + * + * @param breaks The std::vector of the coordinates of break points. */ explicit Impl(std::vector> const& breaks) : Impl(breaks.begin(), breaks.end()) @@ -133,13 +137,16 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase * * The iterators are used to build the DiscreteDomain indexing the knots, build the knots list * and initialize the associated DiscreteSpace. + * + * @param breaks_begin The iterator to begin with to iterate on break points. + * @param breaks_end The iterator to end with to iterate on break points. */ template Impl(RandomIt breaks_begin, RandomIt breaks_end); /** @brief Copy-constructs from another Impl with different Kokkos memory space * - * @param A reference to the other Impl + * @param impl A reference to the other Impl */ template explicit Impl(Impl const& impl) @@ -150,13 +157,13 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase /** @brief Copy-constructs * - * @param A reference to another Impl + * @param x A reference to another Impl */ Impl(Impl const& x) = default; /** @brief Move-constructs * - * @param An rvalue to another Impl + * @param x An rvalue to another Impl */ Impl(Impl&& x) = default; @@ -165,13 +172,13 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase /** @brief Copy-assigns * - * @param A reference to another Impl + * @param x A reference to another Impl */ Impl& operator=(Impl const& x) = default; /** @brief Move-assigns * - * @param An rvalue to another Impl + * @param x An rvalue to another Impl */ Impl& operator=(Impl&& x) = default; diff --git a/include/ddc/kernels/splines/bsplines_uniform.hpp b/include/ddc/kernels/splines/bsplines_uniform.hpp index 570f4cc8e..982fb7415 100644 --- a/include/ddc/kernels/splines/bsplines_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_uniform.hpp @@ -127,7 +127,7 @@ class UniformBSplines : detail::UniformBSplinesBase /** @brief Copy-constructs from another Impl with different Kokkos memory space * - * @param A reference to the other Impl + * @param impl A reference to the other Impl */ template explicit Impl(Impl const& impl) : m_domain(impl.m_domain) @@ -136,13 +136,13 @@ class UniformBSplines : detail::UniformBSplinesBase /** @brief Copy-constructs * - * @param A reference to another Impl + * @param x A reference to another Impl */ Impl(Impl const& x) = default; /** @brief Move-constructs * - * @param An rvalue to another Impl + * @param x An rvalue to another Impl */ Impl(Impl&& x) = default; @@ -151,13 +151,13 @@ class UniformBSplines : detail::UniformBSplinesBase /** @brief Copy-assigns * - * @param A reference to another Impl + * @param x A reference to another Impl */ Impl& operator=(Impl const& x) = default; /** @brief Move-assigns * - * @param An rvalue to another Impl + * @param x An rvalue to another Impl */ Impl& operator=(Impl&& x) = default; From e516124f620f0a04f969966e73f3c2e254b4edff Mon Sep 17 00:00:00 2001 From: blegouix Date: Mon, 22 Apr 2024 17:40:46 +0200 Subject: [PATCH 048/189] CI, integrals doxygen tracking still wrong --- include/ddc/kernels/splines/bsplines_non_uniform.hpp | 2 ++ include/ddc/kernels/splines/bsplines_uniform.hpp | 2 ++ 2 files changed, 4 insertions(+) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index 7139297c9..4ec0315dc 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -173,12 +173,14 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase /** @brief Copy-assigns * * @param x A reference to another Impl + * @return A reference to the copy Impl */ Impl& operator=(Impl const& x) = default; /** @brief Move-assigns * * @param x An rvalue to another Impl + * @return A reference to the moved Impl */ Impl& operator=(Impl&& x) = default; diff --git a/include/ddc/kernels/splines/bsplines_uniform.hpp b/include/ddc/kernels/splines/bsplines_uniform.hpp index 982fb7415..2e7680a2e 100644 --- a/include/ddc/kernels/splines/bsplines_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_uniform.hpp @@ -152,12 +152,14 @@ class UniformBSplines : detail::UniformBSplinesBase /** @brief Copy-assigns * * @param x A reference to another Impl + * @return A reference to the copy Impl */ Impl& operator=(Impl const& x) = default; /** @brief Move-assigns * * @param x An rvalue to another Impl + * @return A reference to the moved Impl */ Impl& operator=(Impl&& x) = default; From a0baf93d5bbbcd4230c75acbe2f2bf5da711b300 Mon Sep 17 00:00:00 2001 From: blegouix Date: Mon, 22 Apr 2024 17:42:28 +0200 Subject: [PATCH 049/189] fix --- include/ddc/kernels/splines/bsplines_uniform.hpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/include/ddc/kernels/splines/bsplines_uniform.hpp b/include/ddc/kernels/splines/bsplines_uniform.hpp index 2e7680a2e..30b4eac71 100644 --- a/include/ddc/kernels/splines/bsplines_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_uniform.hpp @@ -239,7 +239,7 @@ class UniformBSplines : detail::UniformBSplinesBase */ KOKKOS_INLINE_FUNCTION ddc::Coordinate get_knot(int knot_idx) const noexcept { - return ddc::Coordinate(rmin() + idx * ddc::step()); + return ddc::Coordinate(rmin() + knot_idx * ddc::step()); } /** @brief Returns the coordinate of the first support knot associated to a DiscreteElement identifying a B-spline. From d5f56b51ab86f4c3eb403045b80e0be0127b465e Mon Sep 17 00:00:00 2001 From: Baptiste Legouix Date: Mon, 22 Apr 2024 17:44:26 +0200 Subject: [PATCH 050/189] Update include/ddc/kernels/splines/bsplines_non_uniform.hpp Co-authored-by: EmilyBourne --- .../kernels/splines/bsplines_non_uniform.hpp | 17 ++++++++++++----- 1 file changed, 12 insertions(+), 5 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index 4ec0315dc..235db2b94 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -133,13 +133,20 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase { } - /** @brief Constructs a Impl using a pair of iterators. + /** @brief Constructs a Impl by iterating over a set of break points from begin to end. * - * The iterators are used to build the DiscreteDomain indexing the knots, build the knots list - * and initialize the associated DiscreteSpace. + * The provided break points describe the separation between the cells on which the polynomials + * comprising a spline are defined. They are used to build a set of knots. There are 2*degree more + * knots than break points. The knots are defined as follows: + * @f$ k_i = b_0 \forall 0 \leq i < d @f$ + * @f$ k_{i+d} = b_i \forall 0 \leq i < n_b @f$ + * @f$ k_{i+d+n_b} = b_{n_b} \forall 0 \leq i < d @f$ + * where @f$d@f$ is the degree of the polynomials, and @f$n_b@f$ is the number of basis points. * - * @param breaks_begin The iterator to begin with to iterate on break points. - * @param breaks_end The iterator to end with to iterate on break points. + * This constructor makes the knots accessible via a DiscreteSpace. + * + * @param breaks_begin The iterator which points at the beginning of the break points. + * @param breaks_end The iterator which points at the end of the break points. */ template Impl(RandomIt breaks_begin, RandomIt breaks_end); From 29a9c3c98ef49f8915d0e95aa7748babfc85bd63 Mon Sep 17 00:00:00 2001 From: blegouix Date: Tue, 23 Apr 2024 09:50:36 +0200 Subject: [PATCH 051/189] wip --- include/ddc/kernels/splines/bsplines_non_uniform.hpp | 12 ++++++++---- include/ddc/kernels/splines/bsplines_uniform.hpp | 8 ++++---- 2 files changed, 12 insertions(+), 8 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index 4ec0315dc..e43cd1001 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -114,6 +114,8 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase * The brace-list is the list of break points. It is used to build the DiscreteDomain indexing * the knots and iterated over to build the knots coordinates list and initialize the associated DiscreteSpace. * + * @see Impl(RandomIt breaks_begin, RandomIt breaks_end) + * * @param breaks The std::initializer_list of the coordinates of break points. */ explicit Impl(std::initializer_list> breaks) @@ -126,6 +128,8 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase * The std::vector is the list of break points. It is used to build the DiscreteDomain indexing * the knots and iterated over to build the knots coordinates list and initialize the associated DiscreteSpace. * + * @see Impl(RandomIt breaks_begin, RandomIt breaks_end) + * * @param breaks The std::vector of the coordinates of break points. */ explicit Impl(std::vector> const& breaks) @@ -204,7 +208,7 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase * The derivatives are computed for every B-splines with support at the given coordinate x. There are only (degree+1) * B-splines which are non-zero at any given point. It is these B-splines which are derivated. * A spline approximation of a derivative at coordinate x is a linear - * combination of those B-splines derivatives weigthed with splines coefficients of the spline-transformed + * combination of those B-splines derivatives weighted with splines coefficients of the spline-transformed * initial discrete function. * * @param[out] derivs The derivatives of the B-splines evaluated at coordinate x. It has to be a 1D mdspan with (degree+1) elements. @@ -216,10 +220,10 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase /** @brief Evaluates non-zero B-splines values and \f$n\f$ derivatives at a given coordinate * - * The values and derivatives are computed for every B-splines with support at the given coordinate x. There are only (degree+1) - * B-splines which are non-zero at any given point. It is these B-splines which are derivated. + * The values and derivatives are computed for every B-spline with support at the given coordinate x. There are only (degree+1) + * B-splines which are non-zero at any given point. It is these B-splines which are evaluated and derivated. * A spline approximation of a derivative at coordinate x is a linear - * combination of those B-splines derivatives weigthed with splines coefficients of the spline-transformed + * combination of those B-splines derivatives weighted with splines coefficients of the spline-transformed * initial discrete function. * * @param[out] derivs The values and \f$n\f$ derivatives of the B-splines evaluated at coordinate x. It has to be a 2D mdspan with (degree+1)*(n+1) elements. diff --git a/include/ddc/kernels/splines/bsplines_uniform.hpp b/include/ddc/kernels/splines/bsplines_uniform.hpp index 30b4eac71..5d2746e14 100644 --- a/include/ddc/kernels/splines/bsplines_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_uniform.hpp @@ -187,7 +187,7 @@ class UniformBSplines : detail::UniformBSplinesBase * The derivatives are computed for every B-splines with support at the given coordinate x. There are only (degree+1) * B-splines which are non-zero at any given point. It is these B-splines which are derivated. * A spline approximation of a derivative at coordinate x is a linear - * combination of those B-splines derivatives weigthed with splines coefficients of the spline-transformed + * combination of those B-splines derivatives weighted with splines coefficients of the spline-transformed * initial discrete function. * * @param[out] derivs The derivatives of the B-splines evaluated at coordinate x. It has to be a 1D mdspan with (degree+1) elements. @@ -199,10 +199,10 @@ class UniformBSplines : detail::UniformBSplinesBase /** @brief Evaluates non-zero B-splines values and \f$n\f$ derivatives at a given coordinate * - * The values and derivatives are computed for every B-splines with support at the given coordinate x. There are only (degree+1) - * B-splines which are non-zero at any given point. It is these B-splines which are derivated. + * The values and derivatives are computed for every B-spline with support at the given coordinate x. There are only (degree+1) + * B-splines which are non-zero at any given point. It is these B-splines which are evaluated and derivated. * A spline approximation of a derivative at coordinate x is a linear - * combination of those B-splines derivatives weigthed with splines coefficients of the spline-transformed + * combination of those B-splines derivatives weighted with splines coefficients of the spline-transformed * initial discrete function. * * @param[out] derivs The values and \f$n\f$ derivatives of the B-splines evaluated at coordinate x. It has to be a 2D mdspan with (degree+1)*(n+1) elements. From f55723000c33c327469dd62423b676044dd714df Mon Sep 17 00:00:00 2001 From: blegouix Date: Tue, 23 Apr 2024 09:59:07 +0200 Subject: [PATCH 052/189] emily's review --- include/ddc/kernels/splines/bsplines_non_uniform.hpp | 12 ++++++------ include/ddc/kernels/splines/bsplines_uniform.hpp | 7 ++++--- 2 files changed, 10 insertions(+), 9 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index a90ded649..fcd208195 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -142,10 +142,10 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase * The provided break points describe the separation between the cells on which the polynomials * comprising a spline are defined. They are used to build a set of knots. There are 2*degree more * knots than break points. The knots are defined as follows: - * @f$ k_i = b_0 \forall 0 \leq i < d @f$ - * @f$ k_{i+d} = b_i \forall 0 \leq i < n_b @f$ - * @f$ k_{i+d+n_b} = b_{n_b} \forall 0 \leq i < d @f$ - * where @f$d@f$ is the degree of the polynomials, and @f$n_b@f$ is the number of basis points. + * \f$ k_i = b_0 \forall 0 \leq i < d \f$ + * \f$ k_{i+d} = b_i \forall 0 \leq i < n_b \f$ + * \f$ k_{i+d+n_b} = b_{n_b} \forall 0 \leq i < d \f$ + * where \f$d\f$ is the degree of the polynomials, and \f$n_b\f$ is the number of basis points. * * This constructor makes the knots accessible via a DiscreteSpace. * @@ -356,9 +356,9 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase return degree() + ncells(); } - /** @brief Returns the discrete domain including eventual additionnal bsplines in the periodic case. See size(). + /** @brief Returns the discrete domain including eventual additionnal B-splines in the periodic case. See size(). * - * @return The discrete domain including eventual additionnal bsplines. + * @return The discrete domain including eventual additionnal B-splines. */ KOKKOS_INLINE_FUNCTION discrete_domain_type full_domain() const { diff --git a/include/ddc/kernels/splines/bsplines_uniform.hpp b/include/ddc/kernels/splines/bsplines_uniform.hpp index 5d2746e14..930c1075c 100644 --- a/include/ddc/kernels/splines/bsplines_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_uniform.hpp @@ -31,7 +31,8 @@ struct UniformBSplinesBase /** * The type of a uniform B-splines 1D basis. * - * Knots for non-uniform B-splines basis are non-uniformly distributed (no assumption is made on the uniformity of their distribution). + * Knots for uniform B-splines basis are uniformly distributed (the associated discrete dimension + * is a UniformPointSampling). * * @tparam Tag The tag identifying the continuous dimension on which the support of the B-spline functions are defined. * @tparam D The degree of the B-splines. @@ -325,9 +326,9 @@ class UniformBSplines : detail::UniformBSplinesBase return degree() + ncells(); } - /** @brief Returns the discrete domain including eventual additionnal bsplines in the periodic case. See size(). + /** @brief Returns the discrete domain including eventual additionnal B-splines in the periodic case. See size(). * - * @return The discrete domain including eventual additionnal bsplines. + * @return The discrete domain including eventual additionnal B-splines. */ KOKKOS_INLINE_FUNCTION discrete_domain_type full_domain() const { From a0dc60980e3b7ac5450548fa3dc1f0665f604490 Mon Sep 17 00:00:00 2001 From: blegouix Date: Tue, 23 Apr 2024 10:01:33 +0200 Subject: [PATCH 053/189] minor --- include/ddc/kernels/splines/bsplines_non_uniform.hpp | 2 +- include/ddc/kernels/splines/bsplines_uniform.hpp | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index fcd208195..f124a00d2 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -212,7 +212,7 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase /** @brief Evaluates non-zero B-splines derivatives at a given coordinate * - * The derivatives are computed for every B-splines with support at the given coordinate x. There are only (degree+1) + * The derivatives are computed for every B-spline with support at the given coordinate x. There are only (degree+1) * B-splines which are non-zero at any given point. It is these B-splines which are derivated. * A spline approximation of a derivative at coordinate x is a linear * combination of those B-splines derivatives weighted with splines coefficients of the spline-transformed diff --git a/include/ddc/kernels/splines/bsplines_uniform.hpp b/include/ddc/kernels/splines/bsplines_uniform.hpp index 930c1075c..4ffb29694 100644 --- a/include/ddc/kernels/splines/bsplines_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_uniform.hpp @@ -185,7 +185,7 @@ class UniformBSplines : detail::UniformBSplinesBase /** @brief Evaluates non-zero B-splines derivatives at a given coordinate * - * The derivatives are computed for every B-splines with support at the given coordinate x. There are only (degree+1) + * The derivatives are computed for every B-spline with support at the given coordinate x. There are only (degree+1) * B-splines which are non-zero at any given point. It is these B-splines which are derivated. * A spline approximation of a derivative at coordinate x is a linear * combination of those B-splines derivatives weighted with splines coefficients of the spline-transformed From 403a99a5fd94f5b129bc3d2a683dfb0b333fd314 Mon Sep 17 00:00:00 2001 From: blegouix Date: Tue, 23 Apr 2024 10:02:29 +0200 Subject: [PATCH 054/189] minor --- include/ddc/kernels/splines/bsplines_non_uniform.hpp | 4 ++-- include/ddc/kernels/splines/bsplines_uniform.hpp | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index f124a00d2..2a1619fec 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -356,9 +356,9 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase return degree() + ncells(); } - /** @brief Returns the discrete domain including eventual additionnal B-splines in the periodic case. See size(). + /** @brief Returns the discrete domain including eventual additional B-splines in the periodic case. See size(). * - * @return The discrete domain including eventual additionnal B-splines. + * @return The discrete domain including eventual additional B-splines. */ KOKKOS_INLINE_FUNCTION discrete_domain_type full_domain() const { diff --git a/include/ddc/kernels/splines/bsplines_uniform.hpp b/include/ddc/kernels/splines/bsplines_uniform.hpp index 4ffb29694..41bdbf628 100644 --- a/include/ddc/kernels/splines/bsplines_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_uniform.hpp @@ -326,9 +326,9 @@ class UniformBSplines : detail::UniformBSplinesBase return degree() + ncells(); } - /** @brief Returns the discrete domain including eventual additionnal B-splines in the periodic case. See size(). + /** @brief Returns the discrete domain including eventual additional B-splines in the periodic case. See size(). * - * @return The discrete domain including eventual additionnal B-splines. + * @return The discrete domain including eventual additional B-splines. */ KOKKOS_INLINE_FUNCTION discrete_domain_type full_domain() const { From bdd529a5e16fb07f94007258c6cdbab8624d677f Mon Sep 17 00:00:00 2001 From: blegouix Date: Tue, 23 Apr 2024 10:54:57 +0200 Subject: [PATCH 055/189] the spline coefficients --- include/ddc/kernels/splines/bsplines_non_uniform.hpp | 4 ++-- include/ddc/kernels/splines/bsplines_uniform.hpp | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index 2a1619fec..e742e82c0 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -200,7 +200,7 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase * The values are computed for every B-spline with support at the given coordinate x. There are only (degree+1) * B-splines which are non-zero at any given point. It is these B-splines which are evaluated. * This can be useful to calculate a spline approximation of a function. A spline approximation at coordinate x - * is a linear combination of these B-spline evaluations weighted with spline coefficients of the spline-transformed + * is a linear combination of these B-spline evaluations weighted with the spline coefficients of the spline-transformed * initial discrete function. * * @param[out] values The values of the B-splines evaluated at coordinate x. It has to be a 1D mdspan with (degree+1) elements. @@ -215,7 +215,7 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase * The derivatives are computed for every B-spline with support at the given coordinate x. There are only (degree+1) * B-splines which are non-zero at any given point. It is these B-splines which are derivated. * A spline approximation of a derivative at coordinate x is a linear - * combination of those B-splines derivatives weighted with splines coefficients of the spline-transformed + * combination of those B-splines derivatives weighted with the splines coefficients of the spline-transformed * initial discrete function. * * @param[out] derivs The derivatives of the B-splines evaluated at coordinate x. It has to be a 1D mdspan with (degree+1) elements. diff --git a/include/ddc/kernels/splines/bsplines_uniform.hpp b/include/ddc/kernels/splines/bsplines_uniform.hpp index 41bdbf628..de38d5005 100644 --- a/include/ddc/kernels/splines/bsplines_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_uniform.hpp @@ -169,7 +169,7 @@ class UniformBSplines : detail::UniformBSplinesBase * The values are computed for every B-spline with support at the given coordinate x. There are only (degree+1) * B-splines which are non-zero at any given point. It is these B-splines which are evaluated. * This can be useful to calculate a spline approximation of a function. A spline approximation at coordinate x - * is a linear combination of these B-spline evaluations weighted with spline coefficients of the spline-transformed + * is a linear combination of these B-spline evaluations weighted with the spline coefficients of the spline-transformed * initial discrete function. * * @param[out] values The values of the B-splines evaluated at coordinate x. It has to be a 1D mdspan with (degree+1) elements. @@ -188,7 +188,7 @@ class UniformBSplines : detail::UniformBSplinesBase * The derivatives are computed for every B-spline with support at the given coordinate x. There are only (degree+1) * B-splines which are non-zero at any given point. It is these B-splines which are derivated. * A spline approximation of a derivative at coordinate x is a linear - * combination of those B-splines derivatives weighted with splines coefficients of the spline-transformed + * combination of those B-splines derivatives weighted with the splines coefficients of the spline-transformed * initial discrete function. * * @param[out] derivs The derivatives of the B-splines evaluated at coordinate x. It has to be a 1D mdspan with (degree+1) elements. From 8068c3b0ed54902f3c62501ec639bec0a2e8e8b3 Mon Sep 17 00:00:00 2001 From: blegouix Date: Tue, 23 Apr 2024 11:09:45 +0200 Subject: [PATCH 056/189] CI --- .../ddc/kernels/splines/spline_builder.hpp | 28 +++++++++++---- .../ddc/kernels/splines/spline_builder_2d.hpp | 34 +++++++++++++++++++ 2 files changed, 56 insertions(+), 6 deletions(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index 4e0859b7f..9af36aba0 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -17,7 +17,9 @@ namespace ddc { * An enum determining the backend solver of a SplineBuilder or SplineBuilder2d. Only GINKGO available at the moment, * other solvers will be implemented in the futur. */ -enum class SplineSolver { GINKGO }; +enum class SplineSolver { + GINKGO ///< Enum member to identify the Ginkgo-based solver (iterative method) +}; /** * @brief An helper giving the uniform/non_uniform status of a spline interpolation mesh according to its attributes. @@ -28,6 +30,8 @@ enum class SplineSolver { GINKGO }; * @param BcXmin The lower boundary condition. * @param BcXmax The upper boundary condition. * @param degree The degree of the spline. + * + * @return A boolean giving the uniform/non_uniform status. */ constexpr bool is_spline_interpolation_mesh_uniform( bool const is_uniform, @@ -204,12 +208,12 @@ class SplineBuilder // interpolator specific std::unique_ptr matrix; -public: /** * @brief An helper to compute the offset. */ int compute_offset(interpolation_domain_type const& interpolation_domain); +public: /** * @brief Build a SplineBuilder acting on batched_interpolation_domain. * @@ -244,19 +248,31 @@ class SplineBuilder preconditionner_max_block_size); } - /// @brief Copy-constructor is deleted + /** @brief Copy-constructor is deleted + * + * @param x A reference to another SplineBuilder. + */ SplineBuilder(SplineBuilder const& x) = delete; - /// @brief Move-constructs + /** @brief Move-constructs + * + * @param x An rvalue to another SplineBuilder. + */ SplineBuilder(SplineBuilder&& x) = default; /// @brief Destructs ~SplineBuilder() = default; - /// @brief Copy-assignment is deleted + /** @brief Copy-assignment is deleted + * + * @param x A reference to another SplineBuilder. + */ SplineBuilder& operator=(SplineBuilder const& x) = delete; - /// @brief Move-assigns + /** @brief Move-assigns + * + * @param x An rvalue to another SplineBuilder. + */ SplineBuilder& operator=(SplineBuilder&& x) = default; /** diff --git a/include/ddc/kernels/splines/spline_builder_2d.hpp b/include/ddc/kernels/splines/spline_builder_2d.hpp index ae3cfc178..f817d670f 100644 --- a/include/ddc/kernels/splines/spline_builder_2d.hpp +++ b/include/ddc/kernels/splines/spline_builder_2d.hpp @@ -32,10 +32,19 @@ template < class SplineBuilder2D { public: + /** + * @brief The type of the Kokkos execution space used by this class. + */ using exec_space = ExecSpace; + /** + * @brief The type of the Kokkos memory space used by this class. + */ using memory_space = MemorySpace; + /** + * @brief The type of the SplineBuilder used by this class to spline-transform along first dimension. + */ using builder_type1 = ddc::SplineBuilder< ExecSpace, MemorySpace, @@ -45,6 +54,10 @@ class SplineBuilder2D BcXmax1, Solver, IDimX...>; + + /** + * @brief The type of the SplineBuilder used by this class to spline-transform along second dimension. + */ using builder_type2 = ddc::SplineBuilder< ExecSpace, MemorySpace, @@ -54,6 +67,10 @@ class SplineBuilder2D BcXmax2, Solver, std::conditional_t, BSpline1, IDimX>...>; + + /** + * @brief The type of the SplineBuilder used by this class to spline-transform the second-dimension-derivatives along first dimension. + */ using builder_deriv_type1 = ddc::SplineBuilder< ExecSpace, MemorySpace, @@ -72,6 +89,7 @@ class SplineBuilder2D * @brief Tag the dimension of the first 1D SplineBuilder. */ using tag_type1 = typename builder_type1::bsplines_type::tag_type; + /** * @brief Tag the dimension of the second 1D SplineBuilder. */ @@ -82,6 +100,7 @@ class SplineBuilder2D * @brief The type of the BSplines in the first dimension which are compatible with this class. */ using bsplines_type1 = typename builder_type1::bsplines_type; + /** * @brief The type of the BSplines in the second dimension which are compatible with this class. */ @@ -230,6 +249,14 @@ class SplineBuilder2D */ SplineBuilder2D& operator=(SplineBuilder2D&& x) = default; + /** + * @brief Get the whole domain representing interpolation points. + * + * Get the domain on which values of the function must be provided in order + * to build a 2D spline transform of the function. + * + * @return The domain for the grid points. + */ batched_interpolation_domain_type batched_interpolation_domain() const noexcept { return m_spline_builder1.batched_interpolation_domain(); @@ -250,6 +277,13 @@ class SplineBuilder2D m_spline_builder2.interpolation_domain()); } + /** + * @brief Get the batch domain. + * + * Get the batch domain (obtained by removing dimensions of interest from whole interpolation domain). + * + * @return The batch domain. + */ batch_domain_type batch_domain() const noexcept { return ddc::remove_dims_of(batched_interpolation_domain(), interpolation_domain()); From ad555555da49079d7e902ece210216ffb0acacfd Mon Sep 17 00:00:00 2001 From: blegouix Date: Tue, 23 Apr 2024 14:17:24 +0200 Subject: [PATCH 057/189] emily's review --- .../ddc/kernels/splines/bsplines_non_uniform.hpp | 16 ++++++---------- 1 file changed, 6 insertions(+), 10 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index e742e82c0..ea13c032c 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -111,10 +111,8 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase /** @brief Constructs an Impl using a brace-list, i.e. `Impl bsplines({0., 1.})` * - * The brace-list is the list of break points. It is used to build the DiscreteDomain indexing - * the knots and iterated over to build the knots coordinates list and initialize the associated DiscreteSpace. - * - * @see Impl(RandomIt breaks_begin, RandomIt breaks_end) + * Constructs a Impl by iterating over a list of break points. Internally this constructor calls the constructor + * Impl(RandomIt breaks_begin, RandomIt breaks_end). * * @param breaks The std::initializer_list of the coordinates of break points. */ @@ -125,10 +123,8 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase /** @brief Constructs an Impl using a std::vector. * - * The std::vector is the list of break points. It is used to build the DiscreteDomain indexing - * the knots and iterated over to build the knots coordinates list and initialize the associated DiscreteSpace. - * - * @see Impl(RandomIt breaks_begin, RandomIt breaks_end) + * Constructs a Impl by iterating over a list of break points. Internally this constructor calls the constructor + * Impl(RandomIt breaks_begin, RandomIt breaks_end). * * @param breaks The std::vector of the coordinates of break points. */ @@ -215,7 +211,7 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase * The derivatives are computed for every B-spline with support at the given coordinate x. There are only (degree+1) * B-splines which are non-zero at any given point. It is these B-splines which are derivated. * A spline approximation of a derivative at coordinate x is a linear - * combination of those B-splines derivatives weighted with the splines coefficients of the spline-transformed + * combination of those B-splines derivatives weighted with the spline coefficients of the spline-transformed * initial discrete function. * * @param[out] derivs The derivatives of the B-splines evaluated at coordinate x. It has to be a 1D mdspan with (degree+1) elements. @@ -230,7 +226,7 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase * The values and derivatives are computed for every B-spline with support at the given coordinate x. There are only (degree+1) * B-splines which are non-zero at any given point. It is these B-splines which are evaluated and derivated. * A spline approximation of a derivative at coordinate x is a linear - * combination of those B-splines derivatives weighted with splines coefficients of the spline-transformed + * combination of those B-splines derivatives weighted with spline coefficients of the spline-transformed * initial discrete function. * * @param[out] derivs The values and \f$n\f$ derivatives of the B-splines evaluated at coordinate x. It has to be a 2D mdspan with (degree+1)*(n+1) elements. From 45db898b4b2cbe31cf9228427c0ad2bc81bb80cb Mon Sep 17 00:00:00 2001 From: blegouix Date: Tue, 23 Apr 2024 15:59:38 +0200 Subject: [PATCH 058/189] forgot a files save --- include/ddc/kernels/splines/bsplines_uniform.hpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_uniform.hpp b/include/ddc/kernels/splines/bsplines_uniform.hpp index de38d5005..6d6d18e5b 100644 --- a/include/ddc/kernels/splines/bsplines_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_uniform.hpp @@ -188,7 +188,7 @@ class UniformBSplines : detail::UniformBSplinesBase * The derivatives are computed for every B-spline with support at the given coordinate x. There are only (degree+1) * B-splines which are non-zero at any given point. It is these B-splines which are derivated. * A spline approximation of a derivative at coordinate x is a linear - * combination of those B-splines derivatives weighted with the splines coefficients of the spline-transformed + * combination of those B-splines derivatives weighted with the spline coefficients of the spline-transformed * initial discrete function. * * @param[out] derivs The derivatives of the B-splines evaluated at coordinate x. It has to be a 1D mdspan with (degree+1) elements. @@ -203,7 +203,7 @@ class UniformBSplines : detail::UniformBSplinesBase * The values and derivatives are computed for every B-spline with support at the given coordinate x. There are only (degree+1) * B-splines which are non-zero at any given point. It is these B-splines which are evaluated and derivated. * A spline approximation of a derivative at coordinate x is a linear - * combination of those B-splines derivatives weighted with splines coefficients of the spline-transformed + * combination of those B-splines derivatives weighted with spline coefficients of the spline-transformed * initial discrete function. * * @param[out] derivs The values and \f$n\f$ derivatives of the B-splines evaluated at coordinate x. It has to be a 2D mdspan with (degree+1)*(n+1) elements. From 5f821772ac2149066b957461ff94c75c433a9d47 Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 24 Apr 2024 11:37:57 +0200 Subject: [PATCH 059/189] fix doxygen --- include/ddc/kernels/splines/bsplines_non_uniform.hpp | 9 +++++---- include/ddc/kernels/splines/bsplines_uniform.hpp | 9 +++++---- 2 files changed, 10 insertions(+), 8 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index ea13c032c..fc2429b00 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -247,9 +247,10 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase * @return The values of the integrals. */ template - KOKKOS_INLINE_FUNCTION ddc::ChunkSpan - integrals( - ddc::ChunkSpan int_vals) const; + KOKKOS_INLINE_FUNCTION ddc:: + ChunkSpan, Layout, MemorySpace2> + integrals(ddc::ChunkSpan + int_vals) const; /** @brief Returns the coordinate of the knot corresponding to the given index. * @@ -692,7 +693,7 @@ template template KOKKOS_INLINE_FUNCTION ddc::ChunkSpan, Layout, MemorySpace2> NonUniformBSplines::Impl::integrals( - ddc::ChunkSpan, Layout, MemorySpace2> int_vals) const + ddc::ChunkSpan int_vals) const { if constexpr (is_periodic()) { assert(int_vals.size() == nbasis() || int_vals.size() == size()); diff --git a/include/ddc/kernels/splines/bsplines_uniform.hpp b/include/ddc/kernels/splines/bsplines_uniform.hpp index 6d6d18e5b..9f7e65e00 100644 --- a/include/ddc/kernels/splines/bsplines_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_uniform.hpp @@ -224,9 +224,10 @@ class UniformBSplines : detail::UniformBSplinesBase * @return The values of the integrals. */ template - KOKKOS_INLINE_FUNCTION ddc::ChunkSpan - integrals( - ddc::ChunkSpan int_vals) const; + KOKKOS_INLINE_FUNCTION ddc:: + ChunkSpan, Layout, MemorySpace2> + integrals(ddc::ChunkSpan + int_vals) const; /** @brief Returns the coordinate of the knot corresponding to the given index. * @@ -593,7 +594,7 @@ template template KOKKOS_INLINE_FUNCTION ddc::ChunkSpan, Layout, MemorySpace2> UniformBSplines::Impl::integrals( - ddc::ChunkSpan, Layout, MemorySpace2> int_vals) const + ddc::ChunkSpan int_vals) const { if constexpr (is_periodic()) { assert(int_vals.size() == nbasis() || int_vals.size() == size()); From 7dfbed25a4677cb4f4576ab71d8543b1c7119141 Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 24 Apr 2024 12:59:13 +0200 Subject: [PATCH 060/189] clang-format --- include/ddc/kernels/splines/spline_builder.hpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index 9af36aba0..d04954827 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -18,7 +18,7 @@ namespace ddc { * other solvers will be implemented in the futur. */ enum class SplineSolver { - GINKGO ///< Enum member to identify the Ginkgo-based solver (iterative method) + GINKGO ///< Enum member to identify the Ginkgo-based solver (iterative method) }; /** From 669719e03780b6b5248db913cffe5c7a4f752a92 Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 24 Apr 2024 13:15:30 +0200 Subject: [PATCH 061/189] wip on CI --- include/ddc/kernels/splines/spline_builder.hpp | 11 +++-------- include/ddc/kernels/splines/spline_builder_2d.hpp | 9 +++------ 2 files changed, 6 insertions(+), 14 deletions(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index d04954827..9333497d8 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -248,10 +248,7 @@ class SplineBuilder preconditionner_max_block_size); } - /** @brief Copy-constructor is deleted - * - * @param x A reference to another SplineBuilder. - */ + /// @brief Copy-constructor is deleted SplineBuilder(SplineBuilder const& x) = delete; /** @brief Move-constructs @@ -263,15 +260,13 @@ class SplineBuilder /// @brief Destructs ~SplineBuilder() = default; - /** @brief Copy-assignment is deleted - * - * @param x A reference to another SplineBuilder. - */ + /// @brief Copy-assignment is deleted SplineBuilder& operator=(SplineBuilder const& x) = delete; /** @brief Move-assigns * * @param x An rvalue to another SplineBuilder. + * @return A reference to the moved SplineBuilder */ SplineBuilder& operator=(SplineBuilder&& x) = default; diff --git a/include/ddc/kernels/splines/spline_builder_2d.hpp b/include/ddc/kernels/splines/spline_builder_2d.hpp index f817d670f..64e690567 100644 --- a/include/ddc/kernels/splines/spline_builder_2d.hpp +++ b/include/ddc/kernels/splines/spline_builder_2d.hpp @@ -219,12 +219,7 @@ class SplineBuilder2D { } - /** - * @brief Create a new SplineBuilder2D by copy - * - * @param x - * The SplineBuilder2D being copied. - */ + /// @brief Copy-constructor is deleted SplineBuilder2D(SplineBuilder2D const& x) = delete; /** @@ -235,8 +230,10 @@ class SplineBuilder2D */ SplineBuilder2D(SplineBuilder2D&& x) = default; + /// @brief Destructs ~SplineBuilder2D() = default; + /// @brief Copy-assignment is deleted SplineBuilder2D& operator=(SplineBuilder2D const& x) = delete; From 0e27bfeaff554e34c7a588ab751e05f370d57791 Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 24 Apr 2024 13:27:48 +0200 Subject: [PATCH 062/189] null_extrap --- .../ddc/kernels/splines/null_extrapolation_rule.hpp | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/include/ddc/kernels/splines/null_extrapolation_rule.hpp b/include/ddc/kernels/splines/null_extrapolation_rule.hpp index b79fd5850..131eb0af1 100644 --- a/include/ddc/kernels/splines/null_extrapolation_rule.hpp +++ b/include/ddc/kernels/splines/null_extrapolation_rule.hpp @@ -11,6 +11,16 @@ namespace ddc { */ struct NullExtrapolationRule { + /** + * @brief Evaluates 0. out of the domain. + * + * @param[in] pos + * The coordinate where we want to evaluate the function on B-splines. + * @param[in] spline_coef + * The coefficients of the function on B-splines. + * + * @return A double with the value of the function on B-splines evaluated at the coordinate (here, 0.). + */ template KOKKOS_FUNCTION double operator()(CoordType, ChunkSpan) const { From 3982b958dfa1750881dde453541e72cbc7e230b8 Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 24 Apr 2024 13:45:20 +0200 Subject: [PATCH 063/189] CI --- include/ddc/kernels/splines/null_extrapolation_rule.hpp | 5 ----- 1 file changed, 5 deletions(-) diff --git a/include/ddc/kernels/splines/null_extrapolation_rule.hpp b/include/ddc/kernels/splines/null_extrapolation_rule.hpp index 131eb0af1..e7c1348f2 100644 --- a/include/ddc/kernels/splines/null_extrapolation_rule.hpp +++ b/include/ddc/kernels/splines/null_extrapolation_rule.hpp @@ -14,11 +14,6 @@ struct NullExtrapolationRule /** * @brief Evaluates 0. out of the domain. * - * @param[in] pos - * The coordinate where we want to evaluate the function on B-splines. - * @param[in] spline_coef - * The coefficients of the function on B-splines. - * * @return A double with the value of the function on B-splines evaluated at the coordinate (here, 0.). */ template From e302ef9fd17b139e67ae55dec3354423625c6cbc Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 24 Apr 2024 14:55:15 +0200 Subject: [PATCH 064/189] wip --- include/ddc/kernels/splines/spline_builder.hpp | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index 2a20a3caa..63c1bac2b 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -104,7 +104,7 @@ class SplineBuilder using bsplines_type = BSplines; /** - * @brief The Deriv dimension at the boundaries. + * @brief The type of the Deriv dimension at the boundaries. */ using deriv_type = ddc::Deriv; @@ -136,7 +136,7 @@ class SplineBuilder ddc::detail::TypeSeq>>; /** - * @brief The type of the whole spline domain (cartesian product of 1D spline domain and batch domain) with 1D spline domain being contiguous . + * @brief The type of the whole spline domain (cartesian product of 1D spline domain and batch domain) with 1D spline dimension being contiguous . */ using batched_spline_tr_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain>>>; /** - * @brief The type of the whole Derivs domain (cartesian product of 1D Deriv domain and batch domain) preserving the underlying memory layout (order of dimensions). + * @brief The type of the whole Deriv domain (cartesian product of 1D Deriv domain and batch domain) preserving the underlying memory layout (order of dimensions). */ using batched_derivs_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain Date: Wed, 24 Apr 2024 17:49:39 +0200 Subject: [PATCH 065/189] Emily's review --- .../kernels/splines/bsplines_non_uniform.hpp | 28 +++++++++---------- .../ddc/kernels/splines/bsplines_uniform.hpp | 28 +++++++++---------- 2 files changed, 28 insertions(+), 28 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index fc2429b00..4e60efd88 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -29,7 +29,7 @@ struct NonUniformBSplinesBase } // namespace detail /** - * The type of a non-uniform B-splines 1D basis. + * The type of a non-uniform 1D spline basis (B-spline). * * Knots for non-uniform B-splines are non-uniformly distributed (no assumption is made on the uniformity of their distribution, * the associated discrete dimension is a NonUniformPointSampling). @@ -111,7 +111,7 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase /** @brief Constructs an Impl using a brace-list, i.e. `Impl bsplines({0., 1.})` * - * Constructs a Impl by iterating over a list of break points. Internally this constructor calls the constructor + * Constructs an Impl by iterating over a list of break points. Internally this constructor calls the constructor * Impl(RandomIt breaks_begin, RandomIt breaks_end). * * @param breaks The std::initializer_list of the coordinates of break points. @@ -123,7 +123,7 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase /** @brief Constructs an Impl using a std::vector. * - * Constructs a Impl by iterating over a list of break points. Internally this constructor calls the constructor + * Constructs an Impl by iterating over a list of break points. Internally this constructor calls the constructor * Impl(RandomIt breaks_begin, RandomIt breaks_end). * * @param breaks The std::vector of the coordinates of break points. @@ -133,7 +133,7 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase { } - /** @brief Constructs a Impl by iterating over a set of break points from begin to end. + /** @brief Constructs an Impl by iterating over a set of break points from begin to end. * * The provided break points describe the separation between the cells on which the polynomials * comprising a spline are defined. They are used to build a set of knots. There are 2*degree more @@ -151,7 +151,7 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase template Impl(RandomIt breaks_begin, RandomIt breaks_end); - /** @brief Copy-constructs from another Impl with different Kokkos memory space + /** @brief Copy-constructs from another Impl with a different Kokkos memory space * * @param impl A reference to the other Impl */ @@ -180,7 +180,7 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase /** @brief Copy-assigns * * @param x A reference to another Impl - * @return A reference to the copy Impl + * @return A reference to the copied Impl */ Impl& operator=(Impl const& x) = default; @@ -206,32 +206,32 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase KOKKOS_INLINE_FUNCTION discrete_element_type eval_basis(DSpan1D values, ddc::Coordinate const& x) const; - /** @brief Evaluates non-zero B-splines derivatives at a given coordinate + /** @brief Evaluates non-zero B-spline derivatives at a given coordinate * * The derivatives are computed for every B-spline with support at the given coordinate x. There are only (degree+1) * B-splines which are non-zero at any given point. It is these B-splines which are derivated. * A spline approximation of a derivative at coordinate x is a linear - * combination of those B-splines derivatives weighted with the spline coefficients of the spline-transformed + * combination of those B-spline derivatives weighted with the spline coefficients of the spline-transformed * initial discrete function. * * @param[out] derivs The derivatives of the B-splines evaluated at coordinate x. It has to be a 1D mdspan with (degree+1) elements. - * @param[in] x The coordinate where B-splines derivatives are evaluated. + * @param[in] x The coordinate where B-spline derivatives are evaluated. * @return The index of the first B-spline which is derivated. */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_deriv(DSpan1D derivs, ddc::Coordinate const& x) const; - /** @brief Evaluates non-zero B-splines values and \f$n\f$ derivatives at a given coordinate + /** @brief Evaluates non-zero B-spline values and \f$n\f$ derivatives at a given coordinate * * The values and derivatives are computed for every B-spline with support at the given coordinate x. There are only (degree+1) * B-splines which are non-zero at any given point. It is these B-splines which are evaluated and derivated. * A spline approximation of a derivative at coordinate x is a linear - * combination of those B-splines derivatives weighted with spline coefficients of the spline-transformed + * combination of those B-spline derivatives weighted with spline coefficients of the spline-transformed * initial discrete function. * * @param[out] derivs The values and \f$n\f$ derivatives of the B-splines evaluated at coordinate x. It has to be a 2D mdspan with (degree+1)*(n+1) elements. - * @param[in] x The coordinate where B-splines derivatives are evaluated. - * @param[in] n The number of derivatives to evaluate (in addition to the B-splines values themselves). + * @param[in] x The coordinate where B-spline derivatives are evaluated. + * @param[in] n The number of derivatives to evaluate (in addition to the B-spline values themselves). * @return The index of the first B-spline which is evaluated/derivated. */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_basis_and_n_derivs( @@ -255,7 +255,7 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase /** @brief Returns the coordinate of the knot corresponding to the given index. * * Returns the coordinate of the knot corresponding to the given index. The domain - * over which the B-splines are defined is comprised of ncells+1 knots however there are a total of + * over which the B-splines are defined is comprised of ncells+1 break points however there are a total of * ncells+1+2*degree knots. The additional knots which control the shape of the B-splines near the * boundary are added before and after the break points. The knot index is therefore in the interval [-degree, ncells+degree] * diff --git a/include/ddc/kernels/splines/bsplines_uniform.hpp b/include/ddc/kernels/splines/bsplines_uniform.hpp index 9f7e65e00..79a6b5a13 100644 --- a/include/ddc/kernels/splines/bsplines_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_uniform.hpp @@ -29,9 +29,9 @@ struct UniformBSplinesBase } // namespace detail /** - * The type of a uniform B-splines 1D basis. + * The type of a uniform 1D spline basis (B-spline). * - * Knots for uniform B-splines basis are uniformly distributed (the associated discrete dimension + * Knots for uniform B-splines are uniformly distributed (the associated discrete dimension * is a UniformPointSampling). * * @tparam Tag The tag identifying the continuous dimension on which the support of the B-spline functions are defined. @@ -108,7 +108,7 @@ class UniformBSplines : detail::UniformBSplinesBase Impl() = default; - /** Constructs a B-splines basis with n equidistant knots over \f$[a, b]\f$ + /** Constructs a spline basis (B-splines) with n equidistant knots over \f$[a, b]\f$ * * @param rmin the real ddc::coordinate of the first knot * @param rmax the real ddc::coordinate of the last knot @@ -126,7 +126,7 @@ class UniformBSplines : detail::UniformBSplinesBase mesh_type>(rmin, rmax, ddc::DiscreteVector(ncells + 1))); } - /** @brief Copy-constructs from another Impl with different Kokkos memory space + /** @brief Copy-constructs from another Impl with a different Kokkos memory space * * @param impl A reference to the other Impl */ @@ -153,7 +153,7 @@ class UniformBSplines : detail::UniformBSplinesBase /** @brief Copy-assigns * * @param x A reference to another Impl - * @return A reference to the copy Impl + * @return A reference to the copied Impl */ Impl& operator=(Impl const& x) = default; @@ -183,32 +183,32 @@ class UniformBSplines : detail::UniformBSplinesBase return eval_basis(values, x, degree()); } - /** @brief Evaluates non-zero B-splines derivatives at a given coordinate + /** @brief Evaluates non-zero B-spline derivatives at a given coordinate * * The derivatives are computed for every B-spline with support at the given coordinate x. There are only (degree+1) * B-splines which are non-zero at any given point. It is these B-splines which are derivated. * A spline approximation of a derivative at coordinate x is a linear - * combination of those B-splines derivatives weighted with the spline coefficients of the spline-transformed + * combination of those B-spline derivatives weighted with the spline coefficients of the spline-transformed * initial discrete function. * * @param[out] derivs The derivatives of the B-splines evaluated at coordinate x. It has to be a 1D mdspan with (degree+1) elements. - * @param[in] x The coordinate where B-splines derivatives are evaluated. + * @param[in] x The coordinate where B-spline derivatives are evaluated. * @return The index of the first B-spline which is evaluated. */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_deriv(DSpan1D derivs, ddc::Coordinate const& x) const; - /** @brief Evaluates non-zero B-splines values and \f$n\f$ derivatives at a given coordinate + /** @brief Evaluates non-zero B-spline values and \f$n\f$ derivatives at a given coordinate * * The values and derivatives are computed for every B-spline with support at the given coordinate x. There are only (degree+1) * B-splines which are non-zero at any given point. It is these B-splines which are evaluated and derivated. * A spline approximation of a derivative at coordinate x is a linear - * combination of those B-splines derivatives weighted with spline coefficients of the spline-transformed + * combination of those B-spline derivatives weighted with spline coefficients of the spline-transformed * initial discrete function. * * @param[out] derivs The values and \f$n\f$ derivatives of the B-splines evaluated at coordinate x. It has to be a 2D mdspan with (degree+1)*(n+1) elements. - * @param[in] x The coordinate where B-splines derivatives are evaluated. - * @param[in] n The number of derivatives to evaluate (in addition to the B-splines values themselves). + * @param[in] x The coordinate where B-spline derivatives are evaluated. + * @param[in] n The number of derivatives to evaluate (in addition to the B-spline values themselves). * @return The index of the first B-spline which is evaluated. */ KOKKOS_INLINE_FUNCTION discrete_element_type eval_basis_and_n_derivs( @@ -232,9 +232,9 @@ class UniformBSplines : detail::UniformBSplinesBase /** @brief Returns the coordinate of the knot corresponding to the given index. * * Returns the coordinate of the knot corresponding to the given index. The domain - * over which the B-splines are defined is comprised of ncells+1 knots however there are a total of + * over which the B-splines are defined is comprised of ncells+1 break points however there are a total of * ncells+1+2*degree knots. The additional knots which control the shape of the B-splines near the - * boundary are added before and after the break points. The knot index is therefore in the interval [-degree, ncells+degree] + * boundary are added equidistantly before and after the break points. The knot index is therefore in the interval [-degree, ncells+degree] * * @param[in] knot_idx Integer identifying index of the knot. * @return Coordinate of the knot. From 167a36f5156b1af39ae4589d0c5617110822518d Mon Sep 17 00:00:00 2001 From: blegouix Date: Thu, 25 Apr 2024 12:59:23 +0200 Subject: [PATCH 066/189] wip --- .../ddc/kernels/splines/spline_builder.hpp | 28 +++++++++---------- 1 file changed, 14 insertions(+), 14 deletions(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index 7615cfe43..4a51c7bfd 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -50,12 +50,12 @@ constexpr bool is_spline_interpolation_mesh_uniform( * * A class which contains an operator () which can be used to build a spline approximation * of a function. A spline approximation is represented by coefficients stored in a Chunk - * of BSplines. The spline is constructed such that it respects the boundary conditions + * of B-splines. The spline is constructed such that it respects the boundary conditions * BcXmin and BcXmax, and it interpolates the function at the points on the interpolation_mesh * associated with interpolation_mesh_type. * @tparam ExecSpace The Kokkos execution space on which the spline transform is performed. * @tparam MemorySpace The Kokkos memory space on which the data (interpolation function and splines coefficients) are stored. - * @tparam BSplines The discrete dimension representing the BSplines. + * @tparam BSplines The discrete dimension representing the B-splines. * @tparam InterpolationMesh The discrete dimension supporting the interpolation points. * @tparam BcXmin The lower boundary condition. * @tparam BcXmax The upper boundary condition. @@ -99,7 +99,7 @@ class SplineBuilder using interpolation_mesh_type = InterpolationMesh; /** - * @brief The discrete dimension representing the BSplines. + * @brief The discrete dimension representing the B-splines. */ using bsplines_type = BSplines; @@ -252,7 +252,7 @@ class SplineBuilder /** * @brief Get the domain for the 1D interpolation mesh used by this class. * - * Get the 1D interpolation domain associated to dimension of interest. + * This is the 1D because it is defined along the dimension of interest. * * @return The 1D domain for the grid points. */ @@ -264,10 +264,10 @@ class SplineBuilder /** * @brief Get the whole domain representing interpolation points. * - * Get the domain on which values of the function must be provided in order - * to build a spline transform of the function. + * Values of the function must be provided on this domain in order + * to build a spline transform of the function (cartesian product of 1D interpolation_domain and batch_domain). * - * @return The domain for the grid points. + * @return The domain for the interpolation points. */ batched_interpolation_domain_type batched_interpolation_domain() const noexcept { @@ -276,8 +276,8 @@ class SplineBuilder /** * @brief Get the batch domain. - * - * Get the batch domain (obtained by removing dimension of interest from whole interpolation domain). + * + * Obtained by removing dimension of interest from whole interpolation domain. * * @return The batch domain. */ @@ -289,7 +289,7 @@ class SplineBuilder /** * @brief Get the 1D domain on which spline coefficients are defined. * - * Get the 1D spline domain corresponding to dimension of interest. + * The 1D spline domain corresponding to dimension of interest. * * @return The 1D domain for the spline coefficients. */ @@ -301,7 +301,7 @@ class SplineBuilder /** * @brief Get the whole domain on which spline coefficients are defined, preserving memory layout. * - * Get the whole domain on which spline coefficients will be computed, preserving memory layout (order of dimensions). + * The domain on which spline coefficients will be computed, preserving memory layout (order of dimensions). * * @return The domain for the spline coefficients. */ @@ -315,7 +315,7 @@ class SplineBuilder /** * @brief Get the whole domain on which spline coefficients are defined, with dimension of interest contiguous. * - * Get the (transposed) whole domain on which spline coefficients will be computed, with dimension of interest contiguous. + * The (transposed) whole domain on which spline coefficients will be computed, with dimension of interest contiguous. * * @return The (transposed) domain for the spline coefficients. */ @@ -327,7 +327,7 @@ class SplineBuilder /** * @brief Get the whole domain on which derivatives on lower boundary are defined. * - * Get the whole domain on which derivatives on lower boundary are defined. This is used only with HERMITE boundary conditions. + * This is only used with HERMITE boundary conditions. * * @return The domain for the Derivs values. */ @@ -343,7 +343,7 @@ class SplineBuilder /** * @brief Get the whole domain on which derivatives on upper boundary are defined. * - * Get the whole domain on which derivatives on upper boundary are defined. This is used only with HERMITE boundary conditions. + * This is only used with HERMITE boundary conditions. * * @return The domain for the Derivs values. */ From 19e3cc918db28181a722d06f76859e8d30b47022 Mon Sep 17 00:00:00 2001 From: blegouix Date: Thu, 25 Apr 2024 13:26:42 +0200 Subject: [PATCH 067/189] Thomas' review --- .../kernels/splines/bsplines_non_uniform.hpp | 27 ++++++++++--------- .../ddc/kernels/splines/bsplines_uniform.hpp | 12 ++++----- 2 files changed, 21 insertions(+), 18 deletions(-) diff --git a/include/ddc/kernels/splines/bsplines_non_uniform.hpp b/include/ddc/kernels/splines/bsplines_non_uniform.hpp index 4e60efd88..2f1430a8b 100644 --- a/include/ddc/kernels/splines/bsplines_non_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_non_uniform.hpp @@ -76,7 +76,7 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase return false; } - /** @brief Impl Storage class of the static attributes of the discrete dimension. + /** @brief Storage class of the static attributes of the discrete dimension. * * @tparam DDim The name of the discrete dimension. * @tparam MemorySpace The Kokkos memory space where the attributes are being stored. @@ -133,15 +133,18 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase { } - /** @brief Constructs an Impl by iterating over a set of break points from begin to end. + /** @brief Constructs an Impl by iterating over a range of break points from begin to end. * * The provided break points describe the separation between the cells on which the polynomials * comprising a spline are defined. They are used to build a set of knots. There are 2*degree more - * knots than break points. The knots are defined as follows: + * knots than break points. In the non-periodic case the knots are defined as follows: * \f$ k_i = b_0 \forall 0 \leq i < d \f$ * \f$ k_{i+d} = b_i \forall 0 \leq i < n_b \f$ - * \f$ k_{i+d+n_b} = b_{n_b} \forall 0 \leq i < d \f$ - * where \f$d\f$ is the degree of the polynomials, and \f$n_b\f$ is the number of basis points. + * \f$ k_{i+d+n_b} = b_{n_b-1} \forall 0 \leq i < d \f$ + * where \f$d\f$ is the degree of the polynomials, and \f$n_b\f$ is the number of break points in the input pair of iterators. And in the periodic case: + * \f$ k_i = b_{n_b-1-d+i} \forall 0 \leq i < d \f$ + * \f$ k_{i+d} = b_i \forall 0 \leq i \leq n_b \f$ + * \f$ k_{i+d+n_b} = b_{i+1} \forall 0 \leq i < d \f$ * * This constructor makes the knots accessible via a DiscreteSpace. * @@ -200,7 +203,7 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase * initial discrete function. * * @param[out] values The values of the B-splines evaluated at coordinate x. It has to be a 1D mdspan with (degree+1) elements. - * @param[in] x The coordinate where B-splines are evaluated. + * @param[in] x The coordinate where B-splines are evaluated. It has to be in the range of break points coordinates. * @return The index of the first B-spline which is evaluated. */ KOKKOS_INLINE_FUNCTION discrete_element_type @@ -215,7 +218,7 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase * initial discrete function. * * @param[out] derivs The derivatives of the B-splines evaluated at coordinate x. It has to be a 1D mdspan with (degree+1) elements. - * @param[in] x The coordinate where B-spline derivatives are evaluated. + * @param[in] x The coordinate where B-spline derivatives are evaluated. It has to be in the range of break points coordinates. * @return The index of the first B-spline which is derivated. */ KOKKOS_INLINE_FUNCTION discrete_element_type @@ -229,8 +232,8 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase * combination of those B-spline derivatives weighted with spline coefficients of the spline-transformed * initial discrete function. * - * @param[out] derivs The values and \f$n\f$ derivatives of the B-splines evaluated at coordinate x. It has to be a 2D mdspan with (degree+1)*(n+1) elements. - * @param[in] x The coordinate where B-spline derivatives are evaluated. + * @param[out] derivs The values and \f$n\f$ derivatives of the B-splines evaluated at coordinate x. It has to be a 2D mdspan of sizes (degree+1, n+1). + * @param[in] x The coordinate where B-spline derivatives are evaluated. It has to be in the range of break points coordinates. * @param[in] n The number of derivatives to evaluate (in addition to the B-spline values themselves). * @return The index of the first B-spline which is evaluated/derivated. */ @@ -243,7 +246,7 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase * * The integral of each of the B-splines over their support within the domain on which this basis was defined. * - * @param[out] int_vals The values of the integrals. It has to be a 1D mdspan of size (nbasis). + * @param[out] int_vals The values of the integrals. It has to be a 1D Chunkspan of size (nbasis). * @return The values of the integrals. */ template @@ -313,7 +316,7 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase return ddc::coordinate(ddc::DiscreteElement(ix.uid() + n)); } - /** @brief Returns the coordinate of the lower bound of the domain on which the B-splines are defined. + /** @brief Returns the coordinate of the first break point of the domain on which the B-splines are defined. * * @return Coordinate of the lower bound of the domain. */ @@ -322,7 +325,7 @@ class NonUniformBSplines : detail::NonUniformBSplinesBase return get_knot(0); } - /** @brief Returns the coordinate of the upper bound of the domain on which the B-splines are defined. + /** @brief Returns the coordinate of the last break point of the domain on which the B-splines are defined. * * @return Coordinate of the upper bound of the domain. */ diff --git a/include/ddc/kernels/splines/bsplines_uniform.hpp b/include/ddc/kernels/splines/bsplines_uniform.hpp index 79a6b5a13..a11019a42 100644 --- a/include/ddc/kernels/splines/bsplines_uniform.hpp +++ b/include/ddc/kernels/splines/bsplines_uniform.hpp @@ -76,7 +76,7 @@ class UniformBSplines : detail::UniformBSplinesBase return true; } - /** @brief Impl Storage class of the static attributes of the discrete dimension. + /** @brief Storage class of the static attributes of the discrete dimension. * * @tparam DDim The name of the discrete dimension. * @tparam MemorySpace The Kokkos memory space where the attributes are being stored. @@ -173,7 +173,7 @@ class UniformBSplines : detail::UniformBSplinesBase * initial discrete function. * * @param[out] values The values of the B-splines evaluated at coordinate x. It has to be a 1D mdspan with (degree+1) elements. - * @param[in] x The coordinate where B-splines are evaluated. + * @param[in] x The coordinate where B-splines are evaluated. It has to be in the range of break points coordinates. * @return The index of the first B-spline which is evaluated. */ KOKKOS_INLINE_FUNCTION discrete_element_type @@ -192,7 +192,7 @@ class UniformBSplines : detail::UniformBSplinesBase * initial discrete function. * * @param[out] derivs The derivatives of the B-splines evaluated at coordinate x. It has to be a 1D mdspan with (degree+1) elements. - * @param[in] x The coordinate where B-spline derivatives are evaluated. + * @param[in] x The coordinate where B-spline derivatives are evaluated. It has to be in the range of break points coordinates. * @return The index of the first B-spline which is evaluated. */ KOKKOS_INLINE_FUNCTION discrete_element_type @@ -206,8 +206,8 @@ class UniformBSplines : detail::UniformBSplinesBase * combination of those B-spline derivatives weighted with spline coefficients of the spline-transformed * initial discrete function. * - * @param[out] derivs The values and \f$n\f$ derivatives of the B-splines evaluated at coordinate x. It has to be a 2D mdspan with (degree+1)*(n+1) elements. - * @param[in] x The coordinate where B-spline derivatives are evaluated. + * @param[out] derivs The values and \f$n\f$ derivatives of the B-splines evaluated at coordinate x. It has to be a 2D mdspan of sizes (degree+1, n+1). + * @param[in] x The coordinate where B-spline derivatives are evaluated. It has to be in the range of break points coordinates. * @param[in] n The number of derivatives to evaluate (in addition to the B-spline values themselves). * @return The index of the first B-spline which is evaluated. */ @@ -220,7 +220,7 @@ class UniformBSplines : detail::UniformBSplinesBase * * The integral of each of the B-splines over their support within the domain on which this basis was defined. * - * @param[out] int_vals The values of the integrals. It has to be a 1D mdspan of size (nbasis). + * @param[out] int_vals The values of the integrals. It has to be a 1D Chunkspan of size (nbasis). * @return The values of the integrals. */ template From a268a08ca1cc8f1d1c48ecf2c9b03989661e6b3a Mon Sep 17 00:00:00 2001 From: blegouix Date: Thu, 25 Apr 2024 14:38:41 +0200 Subject: [PATCH 068/189] autoreview --- .../ddc/kernels/splines/spline_builder.hpp | 43 ++++---- .../ddc/kernels/splines/spline_builder_2d.hpp | 101 ++++++++---------- 2 files changed, 69 insertions(+), 75 deletions(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index 4a51c7bfd..b6ba4570f 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -252,9 +252,9 @@ class SplineBuilder /** * @brief Get the domain for the 1D interpolation mesh used by this class. * - * This is the 1D because it is defined along the dimension of interest. + * This is 1D because it is defined along the dimension of interest. * - * @return The 1D domain for the grid points. + * @return The 1D domain for the interpolation mesh. */ interpolation_domain_type interpolation_domain() const noexcept { @@ -267,7 +267,7 @@ class SplineBuilder * Values of the function must be provided on this domain in order * to build a spline transform of the function (cartesian product of 1D interpolation_domain and batch_domain). * - * @return The domain for the interpolation points. + * @return The domain for the interpolation mesh. */ batched_interpolation_domain_type batched_interpolation_domain() const noexcept { @@ -289,7 +289,7 @@ class SplineBuilder /** * @brief Get the 1D domain on which spline coefficients are defined. * - * The 1D spline domain corresponding to dimension of interest. + * The 1D spline domain corresponding to the dimension of interest. * * @return The 1D domain for the spline coefficients. */ @@ -301,7 +301,7 @@ class SplineBuilder /** * @brief Get the whole domain on which spline coefficients are defined, preserving memory layout. * - * The domain on which spline coefficients will be computed, preserving memory layout (order of dimensions). + * Spline-transformed functions are computed on this domain. * * @return The domain for the spline coefficients. */ @@ -315,7 +315,7 @@ class SplineBuilder /** * @brief Get the whole domain on which spline coefficients are defined, with dimension of interest contiguous. * - * The (transposed) whole domain on which spline coefficients will be computed, with dimension of interest contiguous. + * This is used internally because of solvers limitation and because it may be beneficial to computation performance. * * @return The (transposed) domain for the spline coefficients. */ @@ -327,7 +327,7 @@ class SplineBuilder /** * @brief Get the whole domain on which derivatives on lower boundary are defined. * - * This is only used with HERMITE boundary conditions. + * This is only used with BoundCond::HERMITE boundary conditions. * * @return The domain for the Derivs values. */ @@ -343,7 +343,7 @@ class SplineBuilder /** * @brief Get the whole domain on which derivatives on upper boundary are defined. * - * This is only used with HERMITE boundary conditions. + * This is only used with BoundCond::HERMITE boundary conditions. * * @return The domain for the Derivs values. */ @@ -359,11 +359,11 @@ class SplineBuilder /** * @brief Get the interpolation matrix. * - * Get the interpolation matrix. This can be useful for debugging (as it allows + * This can be useful for debugging (as it allows * one to print the matrix) or for more complex quadrature schemes. * - * Warning: the returned ddc::detail::Matrix class is not supposed to be exposed - * to user, which means its usage is not tested out of the scope of DDC splines transforms. + * Warning: the returned detail::Matrix class is not supposed to be exposed + * to user, which means its usage is not supported out of the scope of DDC spline transforms. * Use at your own risk. * * @return A reference to the interpolation matrix. @@ -374,22 +374,23 @@ class SplineBuilder } /** - * @brief Build a spline approximation of a function. + * @brief Compute a spline approximation of a function. * - * Use the values of a function at known grid points (as specified by - * SplineBuilder::interpolation_domain) and the derivatives of the - * function at the boundaries (if necessary for the chosen boundary - * conditions) to calculate a spline approximation of a function. + * Use the values of a function (defined on + * SplineBuilder::batched_interpolation_domain) and the derivatives of the + * function at the boundaries (in the case of BoundCond::HERMITE only, defined + * on SplineBuilder::batched_derivs_xmin_domain and SplineBuilder::batched_derivs_xmax_domain) + * to calculate a spline approximation of this function. * * The spline approximation is stored as a ChunkSpan of coefficients - * associated with basis-splines. + * associated with B-splines. * - * @param[out] spline The coefficients of the spline calculated by the function. - * @param[in] vals The values of the function at the grid points. + * @param[out] spline The coefficients of the spline computed by this SplineBuilder. + * @param[in] vals The values of the function on the interpolation mesh. * @param[in] derivs_xmin The values of the derivatives at the lower boundary - * (used only with HERMITE lower boundary condition). + * (used only with BoundCond::HERMITE lower boundary condition). * @param[in] derivs_xmax The values of the derivatives at the upper boundary - * (used only with HERMITE upper boundary condition). + * (used only with BoundCond::HERMITE upper boundary condition). */ template void operator()( diff --git a/include/ddc/kernels/splines/spline_builder_2d.hpp b/include/ddc/kernels/splines/spline_builder_2d.hpp index 64e690567..816ecb82a 100644 --- a/include/ddc/kernels/splines/spline_builder_2d.hpp +++ b/include/ddc/kernels/splines/spline_builder_2d.hpp @@ -12,7 +12,7 @@ namespace ddc { * @brief A class for creating a 2D spline approximation of a function. * * A class which contains an operator () which can be used to build a 2D spline approximation - * of a function. A 2D spline approximation uses a cross-product between two 1D spline builder. + * of a function. A 2D spline approximation uses a cross-product between two 1D SplineBuilder. * * @see SplineBuilder */ @@ -97,44 +97,44 @@ class SplineBuilder2D public: /** - * @brief The type of the BSplines in the first dimension which are compatible with this class. + * @brief The type of the B-splines in the first dimension. */ using bsplines_type1 = typename builder_type1::bsplines_type; /** - * @brief The type of the BSplines in the second dimension which are compatible with this class. + * @brief The type of the B-splines in the second dimension. */ using bsplines_type2 = typename builder_type2::bsplines_type; /** - * @brief The type of the Deriv domain on boundaries in the first dimension which are compatible with this class. + * @brief The type of the Deriv domain on boundaries in the first dimension. */ using deriv_type1 = typename builder_type1::deriv_type; /** - * @brief The type of the Deriv domain on boundaries in the second dimension which are compatible with this class. + * @brief The type of the Deriv domain on boundaries in the second dimension. */ using deriv_type2 = typename builder_type2::deriv_type; /** - * @brief The type of the interpolation mesh in the first dimension used by this class. + * @brief The type of the interpolation mesh in the first dimension. */ using interpolation_mesh_type1 = typename builder_type1::interpolation_mesh_type; /** - * @brief The type of the interpolation mesh in the second dimension used by this class. + * @brief The type of the interpolation mesh in the second dimension. */ using interpolation_mesh_type2 = typename builder_type2::interpolation_mesh_type; /** - * @brief The type of the domain for the interpolation mesh is the first dimension used by this class. + * @brief The type of the domain for the interpolation mesh is the first dimension. */ using interpolation_domain_type1 = typename builder_type1::interpolation_mesh_type; /** - * @brief The type of the domain for the interpolation mesh is the second dimension used by this class. + * @brief The type of the domain for the interpolation mesh is the second dimension. */ using interpolation_domain_type2 = typename builder_type2::interpolation_mesh_type; /** - * @brief The type of the domain for the interpolation mesh is the 2D dimension used by this class. + * @brief The type of the domain for the interpolation mesh is the 2D dimension. */ using interpolation_domain_type = ddc::DiscreteDomain; @@ -145,7 +145,7 @@ class SplineBuilder2D using batched_interpolation_domain_type = ddc::DiscreteDomain; /** - * @brief The type of the batch domain (obtained by removing dimensions of interests from whole space). + * @brief The type of the batch domain (obtained by removing dimensions of interest from whole space). */ using batch_domain_type = ddc::detail::convert_type_seq_to_discrete_domain>>; /** - * @brief The type of the whole Derivs domain (cartesian product of the 1D Deriv domain and the associated batch domain) in the first dimension used by the class, preserving the underlying memory layout (order of dimensions). + * @brief The type of the whole Derivs domain (cartesian product of the 1D Deriv domain and the associated batch domain) in the first dimension, preserving the underlying memory layout (order of dimensions). */ using batched_derivs_domain_type1 = typename builder_type1::batched_derivs_domain_type; /** - * @brief The type of the whole Derivs domain (cartesian product of the 1D Deriv domain and the associated batch domain) in the second dimension used by the class, preserving the underlying memory layout (order of dimensions). + * @brief The type of the whole Derivs domain (cartesian product of the 1D Deriv domain and the associated batch domain) in the second dimension, preserving the underlying memory layout (order of dimensions). */ using batched_derivs_domain_type2 = ddc::detail::convert_type_seq_to_discrete_domain>>; /** - * @brief The type of the whole Derivs domain (cartesian product of the 2D Deriv domain and the batch domain) in the second dimension used by the class, preserving the underlying memory layout (order of dimensions). + * @brief The type of the whole Derivs domain (cartesian product of the 2D Deriv domain and the batch domain) in the second dimension, preserving the underlying memory layout (order of dimensions). */ using batched_derivs_domain_type = ddc::detail::convert_type_seq_to_discrete_domain( + m_spline_builder1.interpolation_domain(), + m_spline_builder2.interpolation_domain()); } /** - * @brief Get the 2D dimension domain from which the approximation is defined. + * @brief Get the whole domain representing interpolation points. * - * Get the 2D dimension domain on which values of the function must be provided in order - * to build a spline approximation of the function. + * Values of the function must be provided on this domain in order + * to build a spline transform of the function (cartesian product of 2D interpolation_domain and batch_domain). * - * @return The 2D dimension domain for the grid points. + * @return The domain for the interpolation mesh. */ - interpolation_domain_type interpolation_domain() const noexcept + batched_interpolation_domain_type batched_interpolation_domain() const noexcept { - return ddc::DiscreteDomain( - m_spline_builder1.interpolation_domain(), - m_spline_builder2.interpolation_domain()); + return m_spline_builder1.batched_interpolation_domain(); } /** * @brief Get the batch domain. * - * Get the batch domain (obtained by removing dimensions of interest from whole interpolation domain). + * Obtained by removing dimensions of interest from whole interpolation domain. * * @return The batch domain. */ @@ -287,15 +282,13 @@ class SplineBuilder2D } /** - * @brief Get the 2D domain on which the approximation is defined. + * @brief Get the 2D domain on which spline coefficients are defined. * - * Get the 2D domain of the basis-splines for which the coefficients of the spline - * approximation must be calculated. + * The 2D spline domain corresponding to the dimensions of interest. * - * @return The 2D domain for the splines. + * @return The 2D domain for the spline coefficients. */ - ddc::DiscreteDomain spline_domain() - const noexcept // TODO : clarify name + ddc::DiscreteDomain spline_domain() const noexcept { return ddc::DiscreteDomain( ddc::discrete_space().full_domain(), @@ -305,7 +298,7 @@ class SplineBuilder2D /** * @brief Get the whole domain on which spline coefficients are defined, preserving memory layout. * - * Get the whole domain on which spline coefficients will be computed, preserving memory layout (order of dimensions). + * Spline-transformed functions are computed on this domain. * * @return The domain for the spline coefficients. */ @@ -319,20 +312,20 @@ class SplineBuilder2D } /** - * @brief Build a 2D spline approximation of a function. - * - * Use the values of a function at known grid points (as specified by - * SplineBuilder2D::interpolation_domain_type) and the derivatives of the - * function at the boundaries (if necessary for the chosen boundary - * conditions) to calculate a 2D spline approximation of a function. + * @brief Compute a 2D spline approximation of a function. * + * Use the values of a function (defined on + * SplineBuilder2D::batched_interpolation_domain) and the derivatives of the + * function at the boundaries (in the case of BoundCond::HERMITE only) + * to calculate a 2D spline approximation of this function. + * * The spline approximation is stored as a ChunkSpan of coefficients - * associated with basis-splines. + * associated with B-splines. * * @param[out] spline - * The coefficients of the spline calculated by the function. + * The coefficients of the spline computed by this SplineBuilder. * @param[in] vals - * The values of the function at the grid points. + * The values of the function at the interpolation mesh. * @param[in] derivs_min1 * The values of the derivatives at the lower boundary in the first dimension. * @param[in] derivs_max1 From a972961c03d541446fef146f37d4badd34394797 Mon Sep 17 00:00:00 2001 From: blegouix Date: Thu, 25 Apr 2024 14:41:28 +0200 Subject: [PATCH 069/189] remove null_extrapolation --- include/ddc/kernels/splines/null_extrapolation_rule.hpp | 8 -------- 1 file changed, 8 deletions(-) diff --git a/include/ddc/kernels/splines/null_extrapolation_rule.hpp b/include/ddc/kernels/splines/null_extrapolation_rule.hpp index e7c1348f2..a81930da6 100644 --- a/include/ddc/kernels/splines/null_extrapolation_rule.hpp +++ b/include/ddc/kernels/splines/null_extrapolation_rule.hpp @@ -6,16 +6,8 @@ namespace ddc { -/** - * @brief A functor for describing a spline boundary value by a null extrapolation for 1D evaluator. - */ struct NullExtrapolationRule { - /** - * @brief Evaluates 0. out of the domain. - * - * @return A double with the value of the function on B-splines evaluated at the coordinate (here, 0.). - */ template KOKKOS_FUNCTION double operator()(CoordType, ChunkSpan) const { From c116d00efc189083c85cfcfadc63509c0c8a175f Mon Sep 17 00:00:00 2001 From: blegouix Date: Thu, 25 Apr 2024 14:45:03 +0200 Subject: [PATCH 070/189] Emily's minireview --- include/ddc/kernels/splines/spline_builder.hpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index b6ba4570f..af186eee0 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -22,9 +22,9 @@ enum class SplineSolver { }; /** - * @brief An helper giving the uniform/non_uniform status of a spline interpolation mesh according to its attributes. + * @brief A helper giving the uniform/non_uniform status of a spline interpolation mesh according to its attributes. * - * An helper giving the uniform/non_uniform status of a spline interpolation mesh according to its attributes. + * A helper giving the uniform/non_uniform status of a spline interpolation mesh according to its attributes. * * @param is_uniform A boolean giving the presumed status before considering boundary conditions. * @param BcXmin The lower boundary condition. From b247fbc63f8cd5002384cbc983db2a1f4ea0292b Mon Sep 17 00:00:00 2001 From: blegouix Date: Thu, 25 Apr 2024 15:57:01 +0200 Subject: [PATCH 071/189] shorten doxygen comments --- .../ddc/kernels/splines/spline_builder.hpp | 64 ++++--------- .../ddc/kernels/splines/spline_builder_2d.hpp | 91 +++++-------------- 2 files changed, 41 insertions(+), 114 deletions(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index af186eee0..3ad17158e 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -83,61 +83,41 @@ class SplineBuilder using tag_type = typename InterpolationMesh::continuous_dimension_type; public: - /** - * @brief The type of the Kokkos execution space used by this class. - */ + /// @brief The type of the Kokkos execution space used by this class. using exec_space = ExecSpace; - /** - * @brief The type of the Kokkos memory space used by this class. - */ + /// @brief The type of the Kokkos memory space used by this class. using memory_space = MemorySpace; - /** - * @brief The type of the interpolation discrete dimension (discrete dimension of interest) used by this class. - */ + /// @brief The type of the interpolation discrete dimension (discrete dimension of interest) used by this class. using interpolation_mesh_type = InterpolationMesh; - /** - * @brief The discrete dimension representing the B-splines. - */ + /// @brief The discrete dimension representing the B-splines. using bsplines_type = BSplines; - /** - * @brief The type of the Deriv dimension at the boundaries. - */ + /// @brief The type of the Deriv dimension at the boundaries. using deriv_type = ddc::Deriv; - /** - * @brief The type of the domain for the 1D interpolation mesh used by this class. - */ + /// @brief The type of the domain for the 1D interpolation mesh used by this class. using interpolation_domain_type = ddc::DiscreteDomain; - /** - * @brief The type of the whole domain representing interpolation points. - */ + /// @brief The type of the whole domain representing interpolation points. using batched_interpolation_domain_type = ddc::DiscreteDomain; - /** - * @brief The type of the batch domain (obtained by removing dimension of interest from whole space). - */ + /// @brief The type of the batch domain (obtained by removing dimension of interest from whole space). using batch_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq>>; - /** - * @brief The type of the whole spline domain (cartesian product of 1D spline domain and batch domain) preserving the underlying memory layout (order of dimensions). - */ + /// @brief The type of the whole spline domain (cartesian product of 1D spline domain and batch domain) preserving the underlying memory layout (order of dimensions). using batched_spline_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq, ddc::detail::TypeSeq>>; - /** - * @brief The type of the whole spline domain (cartesian product of 1D spline domain and batch domain) with 1D spline dimension being contiguous . - */ + /// @brief The type of the whole spline domain (cartesian product of 1D spline domain and batch domain) with 1D spline dimension being contiguous . using batched_spline_tr_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, @@ -145,38 +125,26 @@ class SplineBuilder ddc::detail::TypeSeq, ddc::detail::TypeSeq>>>; - /** - * @brief The type of the whole Deriv domain (cartesian product of 1D Deriv domain and batch domain) preserving the underlying memory layout (order of dimensions). - */ + /// @brief The type of the whole Deriv domain (cartesian product of 1D Deriv domain and batch domain) preserving the underlying memory layout (order of dimensions). using batched_derivs_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq, ddc::detail::TypeSeq>>; - /** - * @brief Indicates if the degree of the splines is odd or even. - */ + /// @brief Indicates if the degree of the splines is odd or even. static constexpr bool s_odd = BSplines::degree() % 2; - /** - * @brief The number of equations defining the boundary condition at the lower bound. - */ + /// @brief The number of equations defining the boundary condition at the lower bound. static constexpr int s_nbc_xmin = n_boundary_equations(BcXmin, BSplines::degree()); - /** - * @brief The number of equations defining the boundary condition at the upper bound. - */ + /// @brief The number of equations defining the boundary condition at the upper bound. static constexpr int s_nbc_xmax = n_boundary_equations(BcXmax, BSplines::degree()); - /** - * @brief The boundary condition implemented at the lower bound. - */ + /// @brief The boundary condition implemented at the lower bound. static constexpr ddc::BoundCond s_bc_xmin = BcXmin; - /** - * @brief The boundary condition implemented at the upper bound. - */ + /// @brief The boundary condition implemented at the upper bound. static constexpr ddc::BoundCond s_bc_xmax = BcXmax; private: diff --git a/include/ddc/kernels/splines/spline_builder_2d.hpp b/include/ddc/kernels/splines/spline_builder_2d.hpp index 816ecb82a..b2aee61ee 100644 --- a/include/ddc/kernels/splines/spline_builder_2d.hpp +++ b/include/ddc/kernels/splines/spline_builder_2d.hpp @@ -32,19 +32,13 @@ template < class SplineBuilder2D { public: - /** - * @brief The type of the Kokkos execution space used by this class. - */ + /// @brief The type of the Kokkos execution space used by this class. using exec_space = ExecSpace; - /** - * @brief The type of the Kokkos memory space used by this class. - */ + /// @brief The type of the Kokkos memory space used by this class. using memory_space = MemorySpace; - /** - * @brief The type of the SplineBuilder used by this class to spline-transform along first dimension. - */ + /// @brief The type of the SplineBuilder used by this class to spline-transform along first dimension. using builder_type1 = ddc::SplineBuilder< ExecSpace, MemorySpace, @@ -55,9 +49,7 @@ class SplineBuilder2D Solver, IDimX...>; - /** - * @brief The type of the SplineBuilder used by this class to spline-transform along second dimension. - */ + /// @brief The type of the SplineBuilder used by this class to spline-transform along second dimension. using builder_type2 = ddc::SplineBuilder< ExecSpace, MemorySpace, @@ -68,9 +60,7 @@ class SplineBuilder2D Solver, std::conditional_t, BSpline1, IDimX>...>; - /** - * @brief The type of the SplineBuilder used by this class to spline-transform the second-dimension-derivatives along first dimension. - */ + /// @brief The type of the SplineBuilder used by this class to spline-transform the second-dimension-derivatives along first dimension. using builder_deriv_type1 = ddc::SplineBuilder< ExecSpace, MemorySpace, @@ -85,99 +75,68 @@ class SplineBuilder2D IDimX>...>; private: - /** - * @brief Tag the dimension of the first 1D SplineBuilder. - */ + /// @brief Tag the dimension of the first 1D SplineBuilder. using tag_type1 = typename builder_type1::bsplines_type::tag_type; - /** - * @brief Tag the dimension of the second 1D SplineBuilder. - */ + /// @brief Tag the dimension of the second 1D SplineBuilder. using tag_type2 = typename builder_type2::bsplines_type::tag_type; public: - /** - * @brief The type of the B-splines in the first dimension. - */ + /// @brief The type of the B-splines in the first dimension. using bsplines_type1 = typename builder_type1::bsplines_type; - /** - * @brief The type of the B-splines in the second dimension. - */ + /// @brief The type of the B-splines in the second dimension. using bsplines_type2 = typename builder_type2::bsplines_type; - /** - * @brief The type of the Deriv domain on boundaries in the first dimension. - */ + /// @brief The type of the Deriv domain on boundaries in the first dimension. using deriv_type1 = typename builder_type1::deriv_type; - /** - * @brief The type of the Deriv domain on boundaries in the second dimension. - */ + /// @brief The type of the Deriv domain on boundaries in the second dimension. using deriv_type2 = typename builder_type2::deriv_type; - /** - * @brief The type of the interpolation mesh in the first dimension. - */ + /// @brief The type of the interpolation mesh in the first dimension. using interpolation_mesh_type1 = typename builder_type1::interpolation_mesh_type; - /** - * @brief The type of the interpolation mesh in the second dimension. - */ + + /// @brief The type of the interpolation mesh in the second dimension. using interpolation_mesh_type2 = typename builder_type2::interpolation_mesh_type; - /** - * @brief The type of the domain for the interpolation mesh is the first dimension. - */ + /// @brief The type of the domain for the interpolation mesh is the first dimension. using interpolation_domain_type1 = typename builder_type1::interpolation_mesh_type; - /** - * @brief The type of the domain for the interpolation mesh is the second dimension. - */ + + /// @brief The type of the domain for the interpolation mesh is the second dimension. using interpolation_domain_type2 = typename builder_type2::interpolation_mesh_type; - /** - * @brief The type of the domain for the interpolation mesh is the 2D dimension. - */ + + /// @brief The type of the domain for the interpolation mesh is the 2D dimension. using interpolation_domain_type = ddc::DiscreteDomain; - /** - * @brief The type of the whole domain representing interpolation points. - */ + /// @brief The type of the whole domain representing interpolation points. using batched_interpolation_domain_type = ddc::DiscreteDomain; - /** - * @brief The type of the batch domain (obtained by removing dimensions of interest from whole space). - */ + /// @brief The type of the batch domain (obtained by removing dimensions of interest from whole space). using batch_domain_type = ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq>>; - /** - * @brief The type of the whole spline domain (cartesian product of 2D spline domain and batch domain) preserving the underlying memory layout (order of dimensions). - */ + /// @brief The type of the whole spline domain (cartesian product of 2D spline domain and batch domain) preserving the underlying memory layout (order of dimensions). using batched_spline_domain_type = ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq, ddc::detail::TypeSeq>>; - /** - * @brief The type of the whole Derivs domain (cartesian product of the 1D Deriv domain and the associated batch domain) in the first dimension, preserving the underlying memory layout (order of dimensions). - */ + /// @brief The type of the whole Derivs domain (cartesian product of the 1D Deriv domain and the associated batch domain) in the first dimension, preserving the underlying memory layout (order of dimensions). using batched_derivs_domain_type1 = typename builder_type1::batched_derivs_domain_type; - /** - * @brief The type of the whole Derivs domain (cartesian product of the 1D Deriv domain and the associated batch domain) in the second dimension, preserving the underlying memory layout (order of dimensions). - */ + /// @brief The type of the whole Derivs domain (cartesian product of the 1D Deriv domain and the associated batch domain) in the second dimension, preserving the underlying memory layout (order of dimensions). using batched_derivs_domain_type2 = ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq, ddc::detail::TypeSeq>>; - /** - * @brief The type of the whole Derivs domain (cartesian product of the 2D Deriv domain and the batch domain) in the second dimension, preserving the underlying memory layout (order of dimensions). - */ + /// @brief The type of the whole Derivs domain (cartesian product of the 2D Deriv domain and the batch domain) in the second dimension, preserving the underlying memory layout (order of dimensions). using batched_derivs_domain_type = ddc::detail::convert_type_seq_to_discrete_domain, From 185ca1132f9f812bd22f0626684256d208025bf6 Mon Sep 17 00:00:00 2001 From: blegouix Date: Fri, 26 Apr 2024 11:04:50 +0200 Subject: [PATCH 072/189] Emily's review --- .../ddc/kernels/splines/spline_builder.hpp | 58 ++++++++++++------- .../ddc/kernels/splines/spline_builder_2d.hpp | 42 ++++++++++---- 2 files changed, 66 insertions(+), 34 deletions(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index 3ad17158e..eef15c403 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -14,8 +14,8 @@ namespace ddc { /** * @brief An enum determining the backend solver of a SplineBuilder or SplineBuilder2d. * - * An enum determining the backend solver of a SplineBuilder or SplineBuilder2d. Only GINKGO available at the moment, - * other solvers will be implemented in the futur. + * An enum determining the backend solver of a SplineBuilder or SplineBuilder2d. Only GINKGO is available at the moment, + * other solvers will be implemented in the future. */ enum class SplineSolver { GINKGO ///< Enum member to identify the Ginkgo-based solver (iterative method) @@ -54,9 +54,9 @@ constexpr bool is_spline_interpolation_mesh_uniform( * BcXmin and BcXmax, and it interpolates the function at the points on the interpolation_mesh * associated with interpolation_mesh_type. * @tparam ExecSpace The Kokkos execution space on which the spline transform is performed. - * @tparam MemorySpace The Kokkos memory space on which the data (interpolation function and splines coefficients) are stored. + * @tparam MemorySpace The Kokkos memory space on which the data (interpolation function and splines coefficients) is stored. * @tparam BSplines The discrete dimension representing the B-splines. - * @tparam InterpolationMesh The discrete dimension supporting the interpolation points. + * @tparam InterpolationMesh The discrete dimension on which interpolation points are defined. * @tparam BcXmin The lower boundary condition. * @tparam BcXmax The upper boundary condition. * @tparam Solver The SplineSolver giving the backend used to perform the spline transform. @@ -104,20 +104,29 @@ class SplineBuilder /// @brief The type of the whole domain representing interpolation points. using batched_interpolation_domain_type = ddc::DiscreteDomain; - /// @brief The type of the batch domain (obtained by removing dimension of interest from whole space). + /** + * @brief The type of the batch domain (obtained by removing the dimension of interest + * from the whole domain). + */ using batch_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq>>; - /// @brief The type of the whole spline domain (cartesian product of 1D spline domain and batch domain) preserving the underlying memory layout (order of dimensions). + /** + * @brief The type of the whole spline domain (cartesian product of 1D spline domain + * and batch domain) preserving the underlying memory layout (order of dimensions). + */ using batched_spline_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq, ddc::detail::TypeSeq>>; - /// @brief The type of the whole spline domain (cartesian product of 1D spline domain and batch domain) with 1D spline dimension being contiguous . + /** + * @brief The type of the whole spline domain (cartesian product of the 1D spline domain + * and the batch domain) with 1D spline dimension being coalescent. + */ using batched_spline_tr_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, @@ -125,7 +134,10 @@ class SplineBuilder ddc::detail::TypeSeq, ddc::detail::TypeSeq>>>; - /// @brief The type of the whole Deriv domain (cartesian product of 1D Deriv domain and batch domain) preserving the underlying memory layout (order of dimensions). + /** + * @brief The type of the whole Deriv domain (cartesian product of 1D Deriv domain + * and batch domain) preserving the underlying memory layout (order of dimensions). + */ using batched_derivs_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, @@ -164,9 +176,11 @@ class SplineBuilder /** * @brief Build a SplineBuilder acting on batched_interpolation_domain. * - * @param batched_interpolation_domain The domain on which are defined the interpolation points. - * @param cols_per_chunk An hyperparameter used by the slicer (internal to the solver) to define the size of a chunk of right-and-sides of the linear problem to be computed in parallel. - * @param preconditionner_max_block_size An hyperparameter used by the slicer (internal to the solver) to define the size of a block used by Block-Jacobi preconditionner. + * @param batched_interpolation_domain The domain on which the interpolation points are defined. + * @param cols_per_chunk A hyperparameter used by the slicer (internal to the solver) to define the size of a chunk of right-and-sides of the linear problem to be computed in parallel. + * @param preconditionner_max_block_size A hyperparameter used by the slicer (internal to the solver) to define the size of a block used by the Block-Jacobi preconditioner. + * + * @see MatrixSparse */ explicit SplineBuilder( batched_interpolation_domain_type const& batched_interpolation_domain, @@ -233,7 +247,7 @@ class SplineBuilder * @brief Get the whole domain representing interpolation points. * * Values of the function must be provided on this domain in order - * to build a spline transform of the function (cartesian product of 1D interpolation_domain and batch_domain). + * to build a spline representation of the function (cartesian product of 1D interpolation_domain and batch_domain). * * @return The domain for the interpolation mesh. */ @@ -245,7 +259,7 @@ class SplineBuilder /** * @brief Get the batch domain. * - * Obtained by removing dimension of interest from whole interpolation domain. + * Obtained by removing the dimension of interest from the whole interpolation domain. * * @return The batch domain. */ @@ -281,7 +295,7 @@ class SplineBuilder } /** - * @brief Get the whole domain on which spline coefficients are defined, with dimension of interest contiguous. + * @brief Get the whole domain on which spline coefficients are defined, with the dimension of interest coalescent. * * This is used internally because of solvers limitation and because it may be beneficial to computation performance. * @@ -329,10 +343,10 @@ class SplineBuilder * * This can be useful for debugging (as it allows * one to print the matrix) or for more complex quadrature schemes. - * - * Warning: the returned detail::Matrix class is not supposed to be exposed - * to user, which means its usage is not supported out of the scope of DDC spline transforms. - * Use at your own risk. + * + * Warning: the returned detail::Matrix class is not supposed to be exposed + * to user, which means its usage is not supported out of the scope of DDC spline transforms. + * Use at your own risk. * * @return A reference to the interpolation matrix. */ @@ -347,8 +361,8 @@ class SplineBuilder * Use the values of a function (defined on * SplineBuilder::batched_interpolation_domain) and the derivatives of the * function at the boundaries (in the case of BoundCond::HERMITE only, defined - * on SplineBuilder::batched_derivs_xmin_domain and SplineBuilder::batched_derivs_xmax_domain) - * to calculate a spline approximation of this function. + * on SplineBuilder::batched_derivs_xmin_domain and SplineBuilder::batched_derivs_xmax_domain) + * to calculate a spline approximation of this function. * * The spline approximation is stored as a ChunkSpan of coefficients * associated with B-splines. @@ -356,9 +370,9 @@ class SplineBuilder * @param[out] spline The coefficients of the spline computed by this SplineBuilder. * @param[in] vals The values of the function on the interpolation mesh. * @param[in] derivs_xmin The values of the derivatives at the lower boundary - * (used only with BoundCond::HERMITE lower boundary condition). + * (used only with BoundCond::HERMITE lower boundary condition). * @param[in] derivs_xmax The values of the derivatives at the upper boundary - * (used only with BoundCond::HERMITE upper boundary condition). + * (used only with BoundCond::HERMITE upper boundary condition). */ template void operator()( diff --git a/include/ddc/kernels/splines/spline_builder_2d.hpp b/include/ddc/kernels/splines/spline_builder_2d.hpp index b2aee61ee..24a8c5c3e 100644 --- a/include/ddc/kernels/splines/spline_builder_2d.hpp +++ b/include/ddc/kernels/splines/spline_builder_2d.hpp @@ -113,30 +113,48 @@ class SplineBuilder2D /// @brief The type of the whole domain representing interpolation points. using batched_interpolation_domain_type = ddc::DiscreteDomain; - /// @brief The type of the batch domain (obtained by removing dimensions of interest from whole space). + /** + * @brief The type of the batch domain (obtained by removing the dimensions of interest + * from the whole domain). + */ using batch_domain_type = ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq>>; - /// @brief The type of the whole spline domain (cartesian product of 2D spline domain and batch domain) preserving the underlying memory layout (order of dimensions). + /** + * @brief The type of the whole spline domain (cartesian product of 2D spline domain + * and batch domain) preserving the underlying memory layout (order of dimensions). + */ using batched_spline_domain_type = ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq, ddc::detail::TypeSeq>>; - /// @brief The type of the whole Derivs domain (cartesian product of the 1D Deriv domain and the associated batch domain) in the first dimension, preserving the underlying memory layout (order of dimensions). + /** + * @brief The type of the whole Derivs domain (cartesian product of the 1D Deriv domain + * and the associated batch domain) in the first dimension, preserving the underlying + * memory layout (order of dimensions). + */ using batched_derivs_domain_type1 = typename builder_type1::batched_derivs_domain_type; - /// @brief The type of the whole Derivs domain (cartesian product of the 1D Deriv domain and the associated batch domain) in the second dimension, preserving the underlying memory layout (order of dimensions). + /** + * @brief The type of the whole Derivs domain (cartesian product of the 1D Deriv domain + * and the associated batch domain) in the second dimension, preserving the underlying + * memory layout (order of dimensions). + */ using batched_derivs_domain_type2 = ddc::detail::convert_type_seq_to_discrete_domain, ddc::detail::TypeSeq, ddc::detail::TypeSeq>>; - /// @brief The type of the whole Derivs domain (cartesian product of the 2D Deriv domain and the batch domain) in the second dimension, preserving the underlying memory layout (order of dimensions). + /** + * @brief The type of the whole Derivs domain (cartesian product of the 2D Deriv domain + * and the batch domain) in the second dimension, preserving the underlying + * memory layout (order of dimensions). + */ using batched_derivs_domain_type = ddc::detail::convert_type_seq_to_discrete_domain, @@ -152,11 +170,11 @@ class SplineBuilder2D /** * @brief Create a new SplineBuilder2D. * - * @param batched_interpolation_domain - * The 2D domain on which points will be provided in order to - * create the 2D spline approximation. - * @param cols_per_chunk The number of columns in the rhs passed to the underlying linear solver. - * @param preconditionner_max_block_size The block size of in the block Jacobi preconditioner. + * @param batched_interpolation_domain The domain on which the interpolation points are defined. + * @param cols_per_chunk A hyperparameter used by the slicer (internal to the solver) to define the size of a chunk of right-and-sides of the linear problem to be computed in parallel. + * @param preconditionner_max_block_size A hyperparameter used by the slicer (internal to the solver) to define the size of a block used by the Block-Jacobi preconditioner. + * + * @see MatrixSparse */ explicit SplineBuilder2D( batched_interpolation_domain_type const& batched_interpolation_domain, @@ -219,7 +237,7 @@ class SplineBuilder2D * @brief Get the whole domain representing interpolation points. * * Values of the function must be provided on this domain in order - * to build a spline transform of the function (cartesian product of 2D interpolation_domain and batch_domain). + * to build a spline representation of the function (cartesian product of 2D interpolation_domain and batch_domain). * * @return The domain for the interpolation mesh. */ @@ -231,7 +249,7 @@ class SplineBuilder2D /** * @brief Get the batch domain. * - * Obtained by removing dimensions of interest from whole interpolation domain. + * Obtained by removing the dimensions of interest from the whole interpolation domain. * * @return The batch domain. */ From 89bff3f8f8898d918b81c6399012a99c4043cde7 Mon Sep 17 00:00:00 2001 From: blegouix Date: Fri, 26 Apr 2024 11:14:36 +0200 Subject: [PATCH 073/189] ident --- .../ddc/kernels/splines/spline_builder.hpp | 4 +-- .../ddc/kernels/splines/spline_builder_2d.hpp | 36 +++++++++---------- 2 files changed, 20 insertions(+), 20 deletions(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index eef15c403..3e2e8bfd7 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -179,8 +179,8 @@ class SplineBuilder * @param batched_interpolation_domain The domain on which the interpolation points are defined. * @param cols_per_chunk A hyperparameter used by the slicer (internal to the solver) to define the size of a chunk of right-and-sides of the linear problem to be computed in parallel. * @param preconditionner_max_block_size A hyperparameter used by the slicer (internal to the solver) to define the size of a block used by the Block-Jacobi preconditioner. - * - * @see MatrixSparse + * + * @see MatrixSparse */ explicit SplineBuilder( batched_interpolation_domain_type const& batched_interpolation_domain, diff --git a/include/ddc/kernels/splines/spline_builder_2d.hpp b/include/ddc/kernels/splines/spline_builder_2d.hpp index 24a8c5c3e..fdce252b2 100644 --- a/include/ddc/kernels/splines/spline_builder_2d.hpp +++ b/include/ddc/kernels/splines/spline_builder_2d.hpp @@ -123,9 +123,9 @@ class SplineBuilder2D ddc::detail::TypeSeq>>; /** - * @brief The type of the whole spline domain (cartesian product of 2D spline domain - * and batch domain) preserving the underlying memory layout (order of dimensions). - */ + * @brief The type of the whole spline domain (cartesian product of 2D spline domain + * and batch domain) preserving the underlying memory layout (order of dimensions). + */ using batched_spline_domain_type = ddc::detail::convert_type_seq_to_discrete_domain, @@ -133,17 +133,17 @@ class SplineBuilder2D ddc::detail::TypeSeq>>; /** - * @brief The type of the whole Derivs domain (cartesian product of the 1D Deriv domain - * and the associated batch domain) in the first dimension, preserving the underlying - * memory layout (order of dimensions). - */ + * @brief The type of the whole Derivs domain (cartesian product of the 1D Deriv domain + * and the associated batch domain) in the first dimension, preserving the underlying + * memory layout (order of dimensions). + */ using batched_derivs_domain_type1 = typename builder_type1::batched_derivs_domain_type; /** - * @brief The type of the whole Derivs domain (cartesian product of the 1D Deriv domain - * and the associated batch domain) in the second dimension, preserving the underlying - * memory layout (order of dimensions). - */ + * @brief The type of the whole Derivs domain (cartesian product of the 1D Deriv domain + * and the associated batch domain) in the second dimension, preserving the underlying + * memory layout (order of dimensions). + */ using batched_derivs_domain_type2 = ddc::detail::convert_type_seq_to_discrete_domain, @@ -151,10 +151,10 @@ class SplineBuilder2D ddc::detail::TypeSeq>>; /** - * @brief The type of the whole Derivs domain (cartesian product of the 2D Deriv domain - * and the batch domain) in the second dimension, preserving the underlying - * memory layout (order of dimensions). - */ + * @brief The type of the whole Derivs domain (cartesian product of the 2D Deriv domain + * and the batch domain) in the second dimension, preserving the underlying + * memory layout (order of dimensions). + */ using batched_derivs_domain_type = ddc::detail::convert_type_seq_to_discrete_domain, @@ -171,10 +171,10 @@ class SplineBuilder2D * @brief Create a new SplineBuilder2D. * * @param batched_interpolation_domain The domain on which the interpolation points are defined. - * @param cols_per_chunk A hyperparameter used by the slicer (internal to the solver) to define the size of a chunk of right-and-sides of the linear problem to be computed in parallel. + * @param cols_per_chunk A hyperparameter used by the slicer (internal to the solver) to define the size of a chunk of right-and-sides of the linear problem to be computed in parallel. * @param preconditionner_max_block_size A hyperparameter used by the slicer (internal to the solver) to define the size of a block used by the Block-Jacobi preconditioner. - * - * @see MatrixSparse + * + * @see MatrixSparse */ explicit SplineBuilder2D( batched_interpolation_domain_type const& batched_interpolation_domain, From bdc3ac852ebc891536a8a8049b738d66543343b4 Mon Sep 17 00:00:00 2001 From: blegouix Date: Tue, 30 Apr 2024 13:21:15 +0200 Subject: [PATCH 074/189] wip --- .../ddc/kernels/splines/spline_builder.hpp | 19 +++++++++++++++---- .../ddc/kernels/splines/spline_builder_2d.hpp | 6 ++++-- 2 files changed, 19 insertions(+), 6 deletions(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index 3e2e8bfd7..9d4e1dfd1 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -107,6 +107,8 @@ class SplineBuilder /** * @brief The type of the batch domain (obtained by removing the dimension of interest * from the whole domain). + * + * Example: For batched_interpolation_domain_type = DiscreteDomain and a dimension of interest Y, this is DiscreteDomain */ using batch_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain and a dimension of interest Y (associated to a B-splines tag BSplinesY), this is DiscreteDomain */ using batched_spline_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain and a dimension of interest Y (associated to a B-splines tag BSplinesY), this is DiscreteDomain */ using batched_spline_tr_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain and a dimension of interest Y, this is DiscreteDomain,Z> */ using batched_derivs_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain Date: Tue, 30 Apr 2024 13:49:13 +0200 Subject: [PATCH 075/189] Emily's review --- include/ddc/kernels/splines/spline_builder.hpp | 6 ++++-- include/ddc/kernels/splines/spline_builder_2d.hpp | 15 +++++++++++++++ 2 files changed, 19 insertions(+), 2 deletions(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index 9d4e1dfd1..0b4bc476f 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -119,7 +119,8 @@ class SplineBuilder * @brief The type of the whole spline domain (cartesian product of 1D spline domain * and batch domain) preserving the underlying memory layout (order of dimensions). * - * Example: For batched_interpolation_domain_type = DiscreteDomain and a dimension of interest Y (associated to a B-splines tag BSplinesY), this is DiscreteDomain + * Example: For batched_interpolation_domain_type = DiscreteDomain and a dimension of interest Y + * (associated to a B-splines tag BSplinesY), this is DiscreteDomain. */ using batched_spline_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain and a dimension of interest Y (associated to a B-splines tag BSplinesY), this is DiscreteDomain + * Example: For batched_interpolation_domain_type = DiscreteDomain and a dimension of interest Y + * (associated to a B-splines tag BSplinesY), this is DiscreteDomain. */ using batched_spline_tr_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain and dimensions of interest X and Y, + * this is DiscreteDomain. */ using batch_domain_type = ddc::detail::convert_type_seq_to_discrete_domain and dimensions of interest X and Y + * (associated to B-splines tags BSplinesX and BSplinesY), this is DiscreteDomain */ using batched_spline_domain_type = ddc::detail::convert_type_seq_to_discrete_domain and dimensions of interest X and Y, + * this is DiscreteDomain, Y, Z>. */ using batched_derivs_domain_type1 = typename builder_type1::batched_derivs_domain_type; @@ -143,6 +152,9 @@ class SplineBuilder2D * @brief The type of the whole Derivs domain (cartesian product of the 1D Deriv domain * and the associated batch domain) in the second dimension, preserving the underlying * memory layout (order of dimensions). + * + * Example: For batched_interpolation_domain_type = DiscreteDomain and dimensions of interest X and Y, + * this is DiscreteDomain, Z>. */ using batched_derivs_domain_type2 = ddc::detail::convert_type_seq_to_discrete_domain and dimensions of interest X and Y, + * this is DiscreteDomain, Deriv, Z>. */ using batched_derivs_domain_type = ddc::detail::convert_type_seq_to_discrete_domain Date: Tue, 30 Apr 2024 13:52:03 +0200 Subject: [PATCH 076/189] minor --- include/ddc/kernels/splines/spline_builder.hpp | 4 ++++ include/ddc/kernels/splines/spline_builder_2d.hpp | 13 +++++++++---- 2 files changed, 13 insertions(+), 4 deletions(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index 0b4bc476f..ac4347a13 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -190,8 +190,12 @@ class SplineBuilder * @param cols_per_chunk A hyperparameter used by the slicer (internal to the solver) to define the size * of a chunk of right-and-sides of the linear problem to be computed in parallel (chunks are treated * by the linear solver one-after-the-other). + * + * This value is optional. If no value is provided then the default value is chosen by the requested solver. * @param preconditionner_max_block_size A hyperparameter used by the slicer (internal to the solver) to * define the size of a block used by the Block-Jacobi preconditioner. + * + * This value is optional. If no value is provided then the default value is chosen by the requested solver. * * @see MatrixSparse */ diff --git a/include/ddc/kernels/splines/spline_builder_2d.hpp b/include/ddc/kernels/splines/spline_builder_2d.hpp index 912f23860..02bb89a88 100644 --- a/include/ddc/kernels/splines/spline_builder_2d.hpp +++ b/include/ddc/kernels/splines/spline_builder_2d.hpp @@ -186,10 +186,15 @@ class SplineBuilder2D * @brief Create a new SplineBuilder2D. * * @param batched_interpolation_domain The domain on which the interpolation points are defined. - * @param cols_per_chunk A hyperparameter used by the slicer (internal to the solver) to define - * the size of a chunk of right-and-sides of the linear problem to be computed in parallel. - * @param preconditionner_max_block_size A hyperparameter used by the slicer (internal to the solver) - * to define the size of a block used by the Block-Jacobi preconditioner. + * @param cols_per_chunk A hyperparameter used by the slicer (internal to the solver) to define the size + * of a chunk of right-and-sides of the linear problem to be computed in parallel (chunks are treated + * by the linear solver one-after-the-other). + * + * This value is optional. If no value is provided then the default value is chosen by the requested solver. + * @param preconditionner_max_block_size A hyperparameter used by the slicer (internal to the solver) to + * define the size of a block used by the Block-Jacobi preconditioner. + * + * This value is optional. If no value is provided then the default value is chosen by the requested solver. * * @see MatrixSparse */ From 127a22be35b15ba79474c2fb6d11b8007d63eb02 Mon Sep 17 00:00:00 2001 From: blegouix Date: Tue, 30 Apr 2024 13:57:11 +0200 Subject: [PATCH 077/189] ident --- .../ddc/kernels/splines/spline_builder.hpp | 34 +++++++++--------- .../ddc/kernels/splines/spline_builder_2d.hpp | 36 +++++++++---------- 2 files changed, 35 insertions(+), 35 deletions(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index ac4347a13..3943908b2 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -116,12 +116,12 @@ class SplineBuilder ddc::detail::TypeSeq>>; /** - * @brief The type of the whole spline domain (cartesian product of 1D spline domain - * and batch domain) preserving the underlying memory layout (order of dimensions). - * - * Example: For batched_interpolation_domain_type = DiscreteDomain and a dimension of interest Y - * (associated to a B-splines tag BSplinesY), this is DiscreteDomain. - */ + * @brief The type of the whole spline domain (cartesian product of 1D spline domain + * and batch domain) preserving the underlying memory layout (order of dimensions). + * + * Example: For batched_interpolation_domain_type = DiscreteDomain and a dimension of interest Y + * (associated to a B-splines tag BSplinesY), this is DiscreteDomain. + */ using batched_spline_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, @@ -129,12 +129,12 @@ class SplineBuilder ddc::detail::TypeSeq>>; /** - * @brief The type of the whole spline domain (cartesian product of the 1D spline domain - * and the batch domain) with 1D spline dimension being the leading dimension. - * - * Example: For batched_interpolation_domain_type = DiscreteDomain and a dimension of interest Y - * (associated to a B-splines tag BSplinesY), this is DiscreteDomain. - */ + * @brief The type of the whole spline domain (cartesian product of the 1D spline domain + * and the batch domain) with 1D spline dimension being the leading dimension. + * + * Example: For batched_interpolation_domain_type = DiscreteDomain and a dimension of interest Y + * (associated to a B-splines tag BSplinesY), this is DiscreteDomain. + */ using batched_spline_tr_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, @@ -143,11 +143,11 @@ class SplineBuilder ddc::detail::TypeSeq>>>; /** - * @brief The type of the whole Deriv domain (cartesian product of 1D Deriv domain - * and batch domain) preserving the underlying memory layout (order of dimensions). - * - * Example: For batched_interpolation_domain_type = DiscreteDomain and a dimension of interest Y, this is DiscreteDomain,Z> - */ + * @brief The type of the whole Deriv domain (cartesian product of 1D Deriv domain + * and batch domain) preserving the underlying memory layout (order of dimensions). + * + * Example: For batched_interpolation_domain_type = DiscreteDomain and a dimension of interest Y, this is DiscreteDomain,Z> + */ using batched_derivs_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, diff --git a/include/ddc/kernels/splines/spline_builder_2d.hpp b/include/ddc/kernels/splines/spline_builder_2d.hpp index 02bb89a88..823be2777 100644 --- a/include/ddc/kernels/splines/spline_builder_2d.hpp +++ b/include/ddc/kernels/splines/spline_builder_2d.hpp @@ -114,12 +114,12 @@ class SplineBuilder2D using batched_interpolation_domain_type = ddc::DiscreteDomain; /** - * @brief The type of the batch domain (obtained by removing the dimensions of interest - * from the whole domain). - * - * Example: For batched_interpolation_domain_type = DiscreteDomain and dimensions of interest X and Y, - * this is DiscreteDomain. - */ + * @brief The type of the batch domain (obtained by removing the dimensions of interest + * from the whole domain). + * + * Example: For batched_interpolation_domain_type = DiscreteDomain and dimensions of interest X and Y, + * this is DiscreteDomain. + */ using batch_domain_type = ddc::detail::convert_type_seq_to_discrete_domain, @@ -128,9 +128,9 @@ class SplineBuilder2D /** * @brief The type of the whole spline domain (cartesian product of 2D spline domain * and batch domain) preserving the underlying memory layout (order of dimensions). - * - * Example: For batched_interpolation_domain_type = DiscreteDomain and dimensions of interest X and Y - * (associated to B-splines tags BSplinesX and BSplinesY), this is DiscreteDomain + * + * Example: For batched_interpolation_domain_type = DiscreteDomain and dimensions of interest X and Y + * (associated to B-splines tags BSplinesX and BSplinesY), this is DiscreteDomain */ using batched_spline_domain_type = ddc::detail::convert_type_seq_to_discrete_domain and dimensions of interest X and Y, - * this is DiscreteDomain, Y, Z>. + * + * Example: For batched_interpolation_domain_type = DiscreteDomain and dimensions of interest X and Y, + * this is DiscreteDomain, Y, Z>. */ using batched_derivs_domain_type1 = typename builder_type1::batched_derivs_domain_type; @@ -152,9 +152,9 @@ class SplineBuilder2D * @brief The type of the whole Derivs domain (cartesian product of the 1D Deriv domain * and the associated batch domain) in the second dimension, preserving the underlying * memory layout (order of dimensions). - * - * Example: For batched_interpolation_domain_type = DiscreteDomain and dimensions of interest X and Y, - * this is DiscreteDomain, Z>. + * + * Example: For batched_interpolation_domain_type = DiscreteDomain and dimensions of interest X and Y, + * this is DiscreteDomain, Z>. */ using batched_derivs_domain_type2 = ddc::detail::convert_type_seq_to_discrete_domain and dimensions of interest X and Y, - * this is DiscreteDomain, Deriv, Z>. + * + * Example: For batched_interpolation_domain_type = DiscreteDomain and dimensions of interest X and Y, + * this is DiscreteDomain, Deriv, Z>. */ using batched_derivs_domain_type = ddc::detail::convert_type_seq_to_discrete_domain Date: Tue, 30 Apr 2024 13:59:39 +0200 Subject: [PATCH 078/189] ident --- include/ddc/kernels/splines/spline_builder.hpp | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index 3943908b2..28ee23f1c 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -188,14 +188,14 @@ class SplineBuilder * * @param batched_interpolation_domain The domain on which the interpolation points are defined. * @param cols_per_chunk A hyperparameter used by the slicer (internal to the solver) to define the size - * of a chunk of right-and-sides of the linear problem to be computed in parallel (chunks are treated - * by the linear solver one-after-the-other). - * - * This value is optional. If no value is provided then the default value is chosen by the requested solver. + * of a chunk of right-and-sides of the linear problem to be computed in parallel (chunks are treated + * by the linear solver one-after-the-other). + * + * This value is optional. If no value is provided then the default value is chosen by the requested solver. * @param preconditionner_max_block_size A hyperparameter used by the slicer (internal to the solver) to - * define the size of a block used by the Block-Jacobi preconditioner. - * - * This value is optional. If no value is provided then the default value is chosen by the requested solver. + * define the size of a block used by the Block-Jacobi preconditioner. + * + * This value is optional. If no value is provided then the default value is chosen by the requested solver. * * @see MatrixSparse */ From d734870731cea555600f89f558c8fb19d0ec5e37 Mon Sep 17 00:00:00 2001 From: blegouix Date: Tue, 30 Apr 2024 14:51:57 +0200 Subject: [PATCH 079/189] minor --- include/ddc/kernels/splines/spline_builder.hpp | 2 +- include/ddc/kernels/splines/spline_builder_2d.hpp | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index 28ee23f1c..c05816f5b 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -188,7 +188,7 @@ class SplineBuilder * * @param batched_interpolation_domain The domain on which the interpolation points are defined. * @param cols_per_chunk A hyperparameter used by the slicer (internal to the solver) to define the size - * of a chunk of right-and-sides of the linear problem to be computed in parallel (chunks are treated + * of a chunk of right-hand-sides of the linear problem to be computed in parallel (chunks are treated * by the linear solver one-after-the-other). * * This value is optional. If no value is provided then the default value is chosen by the requested solver. diff --git a/include/ddc/kernels/splines/spline_builder_2d.hpp b/include/ddc/kernels/splines/spline_builder_2d.hpp index 823be2777..4ebc0e648 100644 --- a/include/ddc/kernels/splines/spline_builder_2d.hpp +++ b/include/ddc/kernels/splines/spline_builder_2d.hpp @@ -187,7 +187,7 @@ class SplineBuilder2D * * @param batched_interpolation_domain The domain on which the interpolation points are defined. * @param cols_per_chunk A hyperparameter used by the slicer (internal to the solver) to define the size - * of a chunk of right-and-sides of the linear problem to be computed in parallel (chunks are treated + * of a chunk of right-hand-sides of the linear problem to be computed in parallel (chunks are treated * by the linear solver one-after-the-other). * * This value is optional. If no value is provided then the default value is chosen by the requested solver. From 68b639e63ac40339c8a5167062af3cae9ab451a2 Mon Sep 17 00:00:00 2001 From: blegouix Date: Tue, 30 Apr 2024 15:13:23 +0200 Subject: [PATCH 080/189] transform -> approximate --- include/ddc/kernels/splines/spline_builder.hpp | 8 ++++---- .../ddc/kernels/splines/spline_builder_2d.hpp | 16 ++++++++-------- 2 files changed, 12 insertions(+), 12 deletions(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index c05816f5b..cfacdc4df 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -53,13 +53,13 @@ constexpr bool is_spline_interpolation_mesh_uniform( * of B-splines. The spline is constructed such that it respects the boundary conditions * BcXmin and BcXmax, and it interpolates the function at the points on the interpolation_mesh * associated with interpolation_mesh_type. - * @tparam ExecSpace The Kokkos execution space on which the spline transform is performed. + * @tparam ExecSpace The Kokkos execution space on which the spline approximation is performed. * @tparam MemorySpace The Kokkos memory space on which the data (interpolation function and splines coefficients) is stored. * @tparam BSplines The discrete dimension representing the B-splines. * @tparam InterpolationMesh The discrete dimension on which interpolation points are defined. * @tparam BcXmin The lower boundary condition. * @tparam BcXmax The upper boundary condition. - * @tparam Solver The SplineSolver giving the backend used to perform the spline transform. + * @tparam Solver The SplineSolver giving the backend used to perform the spline approximation. * @tparam IDimX A variadic template of all the discrete dimensions forming the full space (InterpolationMesh + batched dimensions). */ template < @@ -300,7 +300,7 @@ class SplineBuilder /** * @brief Get the whole domain on which spline coefficients are defined, preserving memory layout. * - * Spline-transformed functions are computed on this domain. + * Spline approximations (spline-transformed functions) are computed on this domain. * * @return The domain for the spline coefficients. */ @@ -362,7 +362,7 @@ class SplineBuilder * one to print the matrix) or for more complex quadrature schemes. * * Warning: the returned detail::Matrix class is not supposed to be exposed - * to user, which means its usage is not supported out of the scope of DDC spline transforms. + * to user, which means its usage is not supported out of the scope of current class. * Use at your own risk. * * @return A reference to the interpolation matrix. diff --git a/include/ddc/kernels/splines/spline_builder_2d.hpp b/include/ddc/kernels/splines/spline_builder_2d.hpp index 4ebc0e648..a1b77e4c6 100644 --- a/include/ddc/kernels/splines/spline_builder_2d.hpp +++ b/include/ddc/kernels/splines/spline_builder_2d.hpp @@ -38,7 +38,7 @@ class SplineBuilder2D /// @brief The type of the Kokkos memory space used by this class. using memory_space = MemorySpace; - /// @brief The type of the SplineBuilder used by this class to spline-transform along first dimension. + /// @brief The type of the SplineBuilder used by this class to spline-approximate along first dimension. using builder_type1 = ddc::SplineBuilder< ExecSpace, MemorySpace, @@ -49,7 +49,7 @@ class SplineBuilder2D Solver, IDimX...>; - /// @brief The type of the SplineBuilder used by this class to spline-transform along second dimension. + /// @brief The type of the SplineBuilder used by this class to spline-approximate along second dimension. using builder_type2 = ddc::SplineBuilder< ExecSpace, MemorySpace, @@ -60,7 +60,7 @@ class SplineBuilder2D Solver, std::conditional_t, BSpline1, IDimX>...>; - /// @brief The type of the SplineBuilder used by this class to spline-transform the second-dimension-derivatives along first dimension. + /// @brief The type of the SplineBuilder used by this class to spline-approximate the second-dimension-derivatives along first dimension. using builder_deriv_type1 = ddc::SplineBuilder< ExecSpace, MemorySpace, @@ -297,7 +297,7 @@ class SplineBuilder2D /** * @brief Get the whole domain on which spline coefficients are defined, preserving memory layout. * - * Spline-transformed functions are computed on this domain. + * Spline approximations (spline-transformed functions) are computed on this domain. * * @return The domain for the spline coefficients. */ @@ -474,7 +474,7 @@ operator()( memory_space>> const mixed_derivs_max1_max2) const { // TODO: perform computations along dimension 1 on different streams ? - // Spline1-transform derivs_min2 (to spline1_deriv_min) + // Spline1-approximate derivs_min2 (to spline1_deriv_min) ddc::Chunk spline1_deriv_min_alloc( m_spline_builder_deriv1.batched_spline_domain(), ddc::KokkosAllocator()); @@ -490,7 +490,7 @@ operator()( spline1_deriv_min_opt = std::nullopt; } - // Spline1-transform vals (to spline1) + // Spline1-approximate vals (to spline1) ddc::Chunk spline1_alloc( m_spline_builder1.batched_spline_domain(), ddc::KokkosAllocator()); @@ -498,7 +498,7 @@ operator()( m_spline_builder1(spline1, vals, derivs_min1, derivs_max1); - // Spline1-transform derivs_max2 (to spline1_deriv_max) + // Spline1-approximate derivs_max2 (to spline1_deriv_max) ddc::Chunk spline1_deriv_max_alloc( m_spline_builder_deriv1.batched_spline_domain(), ddc::KokkosAllocator()); @@ -514,7 +514,7 @@ operator()( spline1_deriv_max_opt = std::nullopt; } - // Spline2-transform spline1 + // Spline2-approximate spline1 m_spline_builder2(spline, spline1.span_cview(), spline1_deriv_min_opt, spline1_deriv_max_opt); } } // namespace ddc From 095635e1a8e5fe364ad00f71752fadd3419171c8 Mon Sep 17 00:00:00 2001 From: blegouix Date: Fri, 3 May 2024 17:18:09 +0200 Subject: [PATCH 081/189] Emily's review --- .../ddc/kernels/splines/spline_builder.hpp | 10 ++++--- .../ddc/kernels/splines/spline_builder_2d.hpp | 26 +++++++++---------- 2 files changed, 19 insertions(+), 17 deletions(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index cfacdc4df..9df081cde 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -108,7 +108,8 @@ class SplineBuilder * @brief The type of the batch domain (obtained by removing the dimension of interest * from the whole domain). * - * Example: For batched_interpolation_domain_type = DiscreteDomain and a dimension of interest Y, this is DiscreteDomain + * Example: For batched_interpolation_domain_type = DiscreteDomain and a dimension of interest Y, + * this is DiscreteDomain */ using batch_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain and a dimension of interest Y, this is DiscreteDomain,Z> + * Example: For batched_interpolation_domain_type = DiscreteDomain and a dimension of interest Y, + * this is DiscreteDomain,Z> */ using batched_derivs_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain; @@ -186,15 +186,15 @@ class SplineBuilder2D * @brief Create a new SplineBuilder2D. * * @param batched_interpolation_domain The domain on which the interpolation points are defined. - * @param cols_per_chunk A hyperparameter used by the slicer (internal to the solver) to define the size - * of a chunk of right-hand-sides of the linear problem to be computed in parallel (chunks are treated - * by the linear solver one-after-the-other). - * - * This value is optional. If no value is provided then the default value is chosen by the requested solver. + * @param cols_per_chunk A hyperparameter used by the slicer (internal to the solver) to define the size + * of a chunk of right-hand-sides of the linear problem to be computed in parallel (chunks are treated + * by the linear solver one-after-the-other). + * + * This value is optional. If no value is provided then the default value is chosen by the requested solver. * @param preconditionner_max_block_size A hyperparameter used by the slicer (internal to the solver) to - * define the size of a block used by the Block-Jacobi preconditioner. - * - * This value is optional. If no value is provided then the default value is chosen by the requested solver. + * define the size of a block used by the Block-Jacobi preconditioner. + * + * This value is optional. If no value is provided then the default value is chosen by the requested solver. * * @see MatrixSparse */ @@ -316,8 +316,8 @@ class SplineBuilder2D * Use the values of a function (defined on * SplineBuilder2D::batched_interpolation_domain) and the derivatives of the * function at the boundaries (in the case of BoundCond::HERMITE only) - * to calculate a 2D spline approximation of this function. - * + * to calculate a 2D spline approximation of this function. + * * The spline approximation is stored as a ChunkSpan of coefficients * associated with B-splines. * From dc4d3f6f0a5de68b1982735e6830ef0bbf34ce2e Mon Sep 17 00:00:00 2001 From: Baptiste Legouix Date: Fri, 3 May 2024 17:18:36 +0200 Subject: [PATCH 082/189] Update include/ddc/kernels/splines/spline_builder.hpp Co-authored-by: EmilyBourne --- include/ddc/kernels/splines/spline_builder.hpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index 9df081cde..cc30765cf 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -189,14 +189,14 @@ class SplineBuilder * @brief Build a SplineBuilder acting on batched_interpolation_domain. * * @param batched_interpolation_domain The domain on which the interpolation points are defined. + * * @param cols_per_chunk A hyperparameter used by the slicer (internal to the solver) to define the size * of a chunk of right-hand-sides of the linear problem to be computed in parallel (chunks are treated * by the linear solver one-after-the-other). - * * This value is optional. If no value is provided then the default value is chosen by the requested solver. + * * @param preconditionner_max_block_size A hyperparameter used by the slicer (internal to the solver) to * define the size of a block used by the Block-Jacobi preconditioner. - * * This value is optional. If no value is provided then the default value is chosen by the requested solver. * * @see MatrixSparse From 927343200e51f427b57fa59524d22071268b016f Mon Sep 17 00:00:00 2001 From: blegouix Date: Mon, 6 May 2024 08:55:16 +0200 Subject: [PATCH 083/189] Emily's review --- include/ddc/kernels/splines/spline_builder.hpp | 10 +++++----- include/ddc/kernels/splines/spline_builder_2d.hpp | 8 ++++---- 2 files changed, 9 insertions(+), 9 deletions(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index cc30765cf..b47ae5d1f 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -105,12 +105,12 @@ class SplineBuilder using batched_interpolation_domain_type = ddc::DiscreteDomain; /** - * @brief The type of the batch domain (obtained by removing the dimension of interest - * from the whole domain). - * - * Example: For batched_interpolation_domain_type = DiscreteDomain and a dimension of interest Y, + * @brief The type of the batch domain (obtained by removing the dimension of interest + * from the whole domain). + * + * Example: For batched_interpolation_domain_type = DiscreteDomain and a dimension of interest Y, * this is DiscreteDomain - */ + */ using batch_domain_type = typename ddc::detail::convert_type_seq_to_discrete_domain, diff --git a/include/ddc/kernels/splines/spline_builder_2d.hpp b/include/ddc/kernels/splines/spline_builder_2d.hpp index ba8666803..a40e38266 100644 --- a/include/ddc/kernels/splines/spline_builder_2d.hpp +++ b/include/ddc/kernels/splines/spline_builder_2d.hpp @@ -183,17 +183,17 @@ class SplineBuilder2D public: /** - * @brief Create a new SplineBuilder2D. - * + * @brief Build a SplineBuilder2D acting on batched_interpolation_domain. + * * @param batched_interpolation_domain The domain on which the interpolation points are defined. + * * @param cols_per_chunk A hyperparameter used by the slicer (internal to the solver) to define the size * of a chunk of right-hand-sides of the linear problem to be computed in parallel (chunks are treated * by the linear solver one-after-the-other). - * * This value is optional. If no value is provided then the default value is chosen by the requested solver. + * * @param preconditionner_max_block_size A hyperparameter used by the slicer (internal to the solver) to * define the size of a block used by the Block-Jacobi preconditioner. - * * This value is optional. If no value is provided then the default value is chosen by the requested solver. * * @see MatrixSparse From 0ddd898cc695ba6f5c75a392b5c4b4fe7d79e88f Mon Sep 17 00:00:00 2001 From: blegouix Date: Mon, 6 May 2024 09:02:51 +0200 Subject: [PATCH 084/189] minor --- include/ddc/kernels/splines/spline_builder_2d.hpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/include/ddc/kernels/splines/spline_builder_2d.hpp b/include/ddc/kernels/splines/spline_builder_2d.hpp index a40e38266..a6aaf571f 100644 --- a/include/ddc/kernels/splines/spline_builder_2d.hpp +++ b/include/ddc/kernels/splines/spline_builder_2d.hpp @@ -183,7 +183,7 @@ class SplineBuilder2D public: /** - * @brief Build a SplineBuilder2D acting on batched_interpolation_domain. + * @brief Build a SplineBuilder2D acting on batched_interpolation_domain. * * @param batched_interpolation_domain The domain on which the interpolation points are defined. * From eef77b965b68896c80b6cb687450ae0bfb248638 Mon Sep 17 00:00:00 2001 From: blegouix Date: Tue, 14 May 2024 18:27:34 +0200 Subject: [PATCH 085/189] hyperparameter -> parameter --- include/ddc/kernels/splines/spline_builder.hpp | 4 ++-- include/ddc/kernels/splines/spline_builder_2d.hpp | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index b47ae5d1f..04d93497b 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -190,12 +190,12 @@ class SplineBuilder * * @param batched_interpolation_domain The domain on which the interpolation points are defined. * - * @param cols_per_chunk A hyperparameter used by the slicer (internal to the solver) to define the size + * @param cols_per_chunk A parameter used by the slicer (internal to the solver) to define the size * of a chunk of right-hand-sides of the linear problem to be computed in parallel (chunks are treated * by the linear solver one-after-the-other). * This value is optional. If no value is provided then the default value is chosen by the requested solver. * - * @param preconditionner_max_block_size A hyperparameter used by the slicer (internal to the solver) to + * @param preconditionner_max_block_size A parameter used by the slicer (internal to the solver) to * define the size of a block used by the Block-Jacobi preconditioner. * This value is optional. If no value is provided then the default value is chosen by the requested solver. * diff --git a/include/ddc/kernels/splines/spline_builder_2d.hpp b/include/ddc/kernels/splines/spline_builder_2d.hpp index a6aaf571f..6eb4f38b8 100644 --- a/include/ddc/kernels/splines/spline_builder_2d.hpp +++ b/include/ddc/kernels/splines/spline_builder_2d.hpp @@ -187,12 +187,12 @@ class SplineBuilder2D * * @param batched_interpolation_domain The domain on which the interpolation points are defined. * - * @param cols_per_chunk A hyperparameter used by the slicer (internal to the solver) to define the size + * @param cols_per_chunk A parameter used by the slicer (internal to the solver) to define the size * of a chunk of right-hand-sides of the linear problem to be computed in parallel (chunks are treated * by the linear solver one-after-the-other). * This value is optional. If no value is provided then the default value is chosen by the requested solver. * - * @param preconditionner_max_block_size A hyperparameter used by the slicer (internal to the solver) to + * @param preconditionner_max_block_size A parameter used by the slicer (internal to the solver) to * define the size of a block used by the Block-Jacobi preconditioner. * This value is optional. If no value is provided then the default value is chosen by the requested solver. * From 932620e9c93df2773c69f0cf7f9d320267023c99 Mon Sep 17 00:00:00 2001 From: Baptiste Legouix Date: Mon, 27 May 2024 11:17:23 +0200 Subject: [PATCH 086/189] Apply suggestions from code review Co-authored-by: Thomas Padioleau --- include/ddc/kernels/splines/spline_builder.hpp | 5 ++--- include/ddc/kernels/splines/spline_builder_2d.hpp | 15 ++++++--------- 2 files changed, 8 insertions(+), 12 deletions(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index bacf17e48..1bd618f5d 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -15,8 +15,7 @@ namespace ddc { /** * @brief An enum determining the backend solver of a SplineBuilder or SplineBuilder2d. * - * An enum determining the backend solver of a SplineBuilder or SplineBuilder2d. Only GINKGO is available at the moment, - * other solvers will be implemented in the future. + * An enum determining the backend solver of a SplineBuilder or SplineBuilder2d. */ enum class SplineSolver { GINKGO ///< Enum member to identify the Ginkgo-based solver (iterative method) @@ -192,7 +191,7 @@ class SplineBuilder * @param batched_interpolation_domain The domain on which the interpolation points are defined. * * @param cols_per_chunk A parameter used by the slicer (internal to the solver) to define the size - * of a chunk of right-hand-sides of the linear problem to be computed in parallel (chunks are treated + * of a chunk of right-hand sides of the linear problem to be computed in parallel (chunks are treated * by the linear solver one-after-the-other). * This value is optional. If no value is provided then the default value is chosen by the requested solver. * diff --git a/include/ddc/kernels/splines/spline_builder_2d.hpp b/include/ddc/kernels/splines/spline_builder_2d.hpp index d9b041cc7..7b635675b 100644 --- a/include/ddc/kernels/splines/spline_builder_2d.hpp +++ b/include/ddc/kernels/splines/spline_builder_2d.hpp @@ -127,7 +127,7 @@ class SplineBuilder2D /** * @brief The type of the whole spline domain (cartesian product of 2D spline domain - * and batch domain) preserving the underlying memory layout (order of dimensions). + * and batch domain) preserving the order of dimensions. * * Example: For batched_interpolation_domain_type = DiscreteDomain and dimensions of interest X and Y * (associated to B-splines tags BSplinesX and BSplinesY), this is DiscreteDomain @@ -140,8 +140,7 @@ class SplineBuilder2D /** * @brief The type of the whole Derivs domain (cartesian product of the 1D Deriv domain - * and the associated batch domain) in the first dimension, preserving the underlying - * memory layout (order of dimensions). + * and the associated batch domain) in the first dimension, preserving the order of dimensions. * * Example: For batched_interpolation_domain_type = DiscreteDomain and dimensions of interest X and Y, * this is DiscreteDomain, Y, Z>. @@ -150,8 +149,7 @@ class SplineBuilder2D /** * @brief The type of the whole Derivs domain (cartesian product of the 1D Deriv domain - * and the associated batch domain) in the second dimension, preserving the underlying - * memory layout (order of dimensions). + * and the associated batch domain) in the second dimension, preserving the order of dimensions. * * Example: For batched_interpolation_domain_type = DiscreteDomain and dimensions of interest X and Y, * this is DiscreteDomain, Z>. @@ -164,8 +162,7 @@ class SplineBuilder2D /** * @brief The type of the whole Derivs domain (cartesian product of the 2D Deriv domain - * and the batch domain) in the second dimension, preserving the underlying - * memory layout (order of dimensions). + * and the batch domain) in the second dimension, preserving the order of dimensions. * * Example: For batched_interpolation_domain_type = DiscreteDomain and dimensions of interest X and Y, * this is DiscreteDomain, Deriv, Z>. @@ -196,7 +193,7 @@ class SplineBuilder2D * define the size of a block used by the Block-Jacobi preconditioner. * This value is optional. If no value is provided then the default value is chosen by the requested solver. * - * @see MatrixSparse + * @see SplinesLinearProblemSparse */ explicit SplineBuilder2D( batched_interpolation_domain_type const& batched_interpolation_domain, @@ -295,7 +292,7 @@ class SplineBuilder2D } /** - * @brief Get the whole domain on which spline coefficients are defined, preserving memory layout. + * @brief Get the whole domain on which spline coefficients are defined. * * Spline approximations (spline-transformed functions) are computed on this domain. * From b3d9c544a1f55391d997a8c9322d7976f369dc43 Mon Sep 17 00:00:00 2001 From: blegouix Date: Mon, 27 May 2024 11:24:30 +0200 Subject: [PATCH 087/189] privatize transposed-domain functions --- include/ddc/kernels/splines/spline_builder.hpp | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index 1bd618f5d..4bdfe7583 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -129,6 +129,7 @@ class SplineBuilder ddc::detail::TypeSeq, ddc::detail::TypeSeq>>; +private: /** * @brief The type of the whole spline domain (cartesian product of the 1D spline domain * and the batch domain) with 1D spline dimension being the leading dimension. @@ -143,6 +144,7 @@ class SplineBuilder ddc::detail::TypeSeq, ddc::detail::TypeSeq>>>; +public: /** * @brief The type of the whole Deriv domain (cartesian product of 1D Deriv domain * and batch domain) preserving the underlying memory layout (order of dimensions). @@ -313,6 +315,7 @@ class SplineBuilder bsplines_type>(batched_interpolation_domain(), spline_domain()); } +private: /** * @brief Get the whole domain on which spline coefficients are defined, with the dimension of interest being the leading dimension. * @@ -325,6 +328,7 @@ class SplineBuilder return batched_spline_tr_domain_type(spline_domain(), batch_domain()); } +public: /** * @brief Get the whole domain on which derivatives on lower boundary are defined. * From bc8ce54720d29fe55b6513ef4933554e8204a6be Mon Sep 17 00:00:00 2001 From: Baptiste Legouix Date: Mon, 27 May 2024 11:27:07 +0200 Subject: [PATCH 088/189] Update include/ddc/kernels/splines/spline_builder.hpp Co-authored-by: Thomas Padioleau --- include/ddc/kernels/splines/spline_builder.hpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index 4bdfe7583..001c49069 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -302,7 +302,7 @@ class SplineBuilder } /** - * @brief Get the whole domain on which spline coefficients are defined, preserving memory layout. + * @brief Get the whole domain on which spline coefficients are defined. * * Spline approximations (spline-transformed functions) are computed on this domain. * From 2b9071a86f8001d0589605cc1eabe2eb96342e4b Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 29 May 2024 14:27:34 +0200 Subject: [PATCH 089/189] wip --- .../splines_linear_problem_corner_block.hpp | 307 ++++++++++++++++++ 1 file changed, 307 insertions(+) create mode 100644 include/ddc/kernels/splines/splines_linear_problem_corner_block.hpp diff --git a/include/ddc/kernels/splines/splines_linear_problem_corner_block.hpp b/include/ddc/kernels/splines/splines_linear_problem_corner_block.hpp new file mode 100644 index 000000000..0f9cdf0cc --- /dev/null +++ b/include/ddc/kernels/splines/splines_linear_problem_corner_block.hpp @@ -0,0 +1,307 @@ +// Copyright (C) The DDC development team, see COPYRIGHT.md file +// +// SPDX-License-Identifier: MIT + +#pragma once + +#include +#include +#include + +#if __has_include() +#include +#else +#include +#endif + +#include "splines_linear_problem.hpp" + +namespace ddc::detail { + +/** + * @brief A 2x2-blocks linear problem dedicated to the computation of a spline approximation, with all blocks except top-left being stored in dense format. + * + * The storage format is dense row-major for top-left and bottom-right blocks, the one of SplinesLinearProblemDense (which is also dense row-major in practice) for bottom-right block and undefined for the top-left one (determined by the type of q_block). + * + * This class implements a Schur complement method to perform a block-LU factorization and solve, calling tl_block and br_block setup_solver() and solve() methods for internal operations. + * + * @tparam ExecSpace The Kokkos::ExecutionSpace on which operations related to the matrix are supposed to be performed. + */ +template +class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem +{ +public: + using typename SplinesLinearProblem::MultiRHS; + using SplinesLinearProblem::size; + +protected: + std::size_t const m_k; // small block size + std::size_t const m_nb; // main block matrix size + //------------------------------------- + // + // q = | q_block | gamma | + // | lambda | delta | + // + //------------------------------------- + std::shared_ptr m_q_block; + std::shared_ptr> m_delta; + Kokkos::View m_Abm_1_gamma; + Kokkos::View m_lambda; + +public: + /** + * @brief SplinesLinearProblem2x2Blocks constructor. + * + * @param mat_size The size of one of the dimensions of the square matrix. + */ + explicit SplinesLinearProblem2x2Blocks( + std::size_t const mat_size, + std::size_t const k, + std::unique_ptr> q) + : SplinesLinearProblem(mat_size) + , m_k(k) + , m_nb(mat_size - k) + , m_q_block(std::move(q)) + , m_delta(new SplinesLinearSolver(k)) + , m_Abm_1_gamma("Abm_1_gamma", m_nb, m_k) + , m_lambda("lambda", m_k, m_nb) + { + assert(m_k <= mat_size); + assert(m_nb == m_q_block->size()); // TODO: remove + + Kokkos::deep_copy(m_Abm_1_gamma, 0.); + Kokkos::deep_copy(m_lambda, 0.); + } + +protected: + explicit SplinesLinearProblem2x2Blocks( + std::size_t const n, + std::size_t const k, + std::unique_ptr> q, + std::size_t const lambda_size1, + std::size_t const lambda_size2) + : SplinesLinearProblem(mat_size) + , m_k(k) + , m_nb(mat_size - k) + , m_q_block(std::move(q)) + , m_delta(new MatrixDense(k)) + , m_Abm_1_gamma("Abm_1_gamma", m_nb, m_k) + , m_lambda("lambda", lambda_size1, lambda_size2) + { + assert(m_k <= mat_size); + assert(m_nb == m_q_block->size()); // TODO: remove + + Kokkos::deep_copy(m_Abm_1_gamma, 0.); + Kokkos::deep_copy(m_lambda, 0.); + } + +public: + virtual double get_element(std::size_t const i, std::size_t const j) const override + { + assert(i < size()); + assert(j < size()); + + if (i < m_nb && j < m_nb) { + return m_q_block->get_element(i, j); + } else if (i >= m_nb && j >= m_nb) { + return m_delta->get_element(i - m_nb, j - m_nb); + } else if (j >= m_nb) { + return m_Abm_1_gamma(i, j - m_nb); + } else { + return m_lambda(i - m_nb, j); + } + } + + virtual void set_element(std::size_t const i, std::size_t const j, double const aij) override + { + assert(i < size()); + assert(j < size()); + + if (i < m_nb && j < m_nb) { + m_q_block->set_element(i, j, aij); + } else if (i >= m_nb && j >= m_nb) { + m_delta->set_element(i - m_nb, j - m_nb, aij); + } else if (j >= m_nb) { + m_Abm_1_gamma(i, j - m_nb) = aij; + } else { + m_lambda(i - m_nb, j) = aij; + } + } + +private: + virtual void calculate_delta_to_factorize() + { + Kokkos::parallel_for( + "calculate_delta_to_factorize", + Kokkos::MDRangePolicy< + Kokkos::DefaultHostExecutionSpace, + Kokkos::Rank<2>>({0, 0}, {m_k, m_k}), + [&](const int i, const int j) { + double val = 0.0; + for (int l = 0; l < m_nb; ++l) { + val += m_lambda(i, l) * m_Abm_1_gamma(l, j); + } + delta.set_element(i, j, delta.get_element(i, j) - val); + }); + } + +public: + /** + * @brief Perform a pre-process operation on the solver. Must be called after filling the matrix. + * + * Block-LU factorize the matrix A according to the Schur complement method. + */ + void setup_solver() override + { + m_q_block->setup_solver(); + m_q_block->solve_inplace(m_Abm_1_gamma); + calculate_delta_to_factorize(); + m_delta->setup_solver(); + } + +private: + virtual ddc::DSpan2D_stride solve_lambda_section( + ddc::DSpan2D_stride const v, + ddc::DView2D_stride const u) const + { + auto lambda_device = create_mirror_view_and_copy(ExecSpace(), m_lambda); + auto nb_proxy = m_nb; + auto k_proxy = m_k; + Kokkos::parallel_for( + "solve_lambda_section", + Kokkos::TeamPolicy(v.extent(1), Kokkos::AUTO), + KOKKOS_LAMBDA( + const typename Kokkos::TeamPolicy::member_type& teamMember) { + const int j = teamMember.league_rank(); + + + Kokkos::parallel_for( + Kokkos::TeamThreadRange(teamMember, k_proxy), + [&](const int i) { + // Upper diagonals in lambda + for (int l = 0; l < nb_proxy; ++l) { + v(i, j) -= lambda_device(i, l) * u(l, j); + } + }); + }); + return v; + } + + virtual ddc::DSpan2D_stride solve_lambda_section_transpose( + ddc::DSpan2D_stride const u, + ddc::DView2D_stride const v) const + { + auto lambda_device = create_mirror_view_and_copy(ExecSpace(), m_lambda); + auto nb_proxy = m_nb; + auto k_proxy = m_k; + Kokkos::parallel_for( + "solve_lambda_section_transpose", + Kokkos::TeamPolicy(u.extent(1), Kokkos::AUTO), + KOKKOS_LAMBDA( + const typename Kokkos::TeamPolicy::member_type& teamMember) { + const int j = teamMember.league_rank(); + + + Kokkos::parallel_for( + Kokkos::TeamThreadRange(teamMember, nb_proxy), + [&](const int i) { + // Upper diagonals in lambda + for (int l = 0; l < k_proxy; ++l) { + u(i, j) -= lambda_device(l, i) * v(l, j); + } + }); + }); + return u; + } + + virtual ddc::DSpan2D_stride solve_gamma_section( + ddc::DSpan2D_stride const u, + ddc::DView2D_stride const v) const + { + auto Abm_1_gamma_device = create_mirror_view_and_copy(ExecSpace(), m_Abm_1_gamma); + auto nb_proxy = m_nb; + auto k_proxy = m_k; + Kokkos::parallel_for( + "solve_gamma_section", + Kokkos::TeamPolicy(u.extent(1), Kokkos::AUTO), + KOKKOS_LAMBDA( + const typename Kokkos::TeamPolicy::member_type& teamMember) { + const int j = teamMember.league_rank(); + + + Kokkos::parallel_for( + Kokkos::TeamThreadRange(teamMember, nb_proxy), + [&](const int i) { + // Upper diagonals in lambda + for (int l = 0; l < k_proxy; ++l) { + u(i, j) -= Abm_1_gamma_device(i, l) * v(l, j); + } + }); + }); + return u; + } + + virtual ddc::DSpan2D_stride solve_gamma_section_transpose( + ddc::DSpan2D_stride const v, + ddc::DView2D_stride const u) const + { + auto Abm_1_gamma_device = create_mirror_view_and_copy(ExecSpace(), m_Abm_1_gamma); + auto nb_proxy = m_nb; + auto k_proxy = m_k; + Kokkos::parallel_for( + "solve_gamma_section_transpose", + Kokkos::TeamPolicy(v.extent(1), Kokkos::AUTO), + KOKKOS_LAMBDA( + const typename Kokkos::TeamPolicy::member_type& teamMember) { + const int j = teamMember.league_rank(); + + + Kokkos::parallel_for( + Kokkos::TeamThreadRange(teamMember, k_proxy), + [&](const int i) { + // Upper diagonals in lambda + for (int l = 0; l < nb_proxy; ++l) { + v(i, j) -= Abm_1_gamma_device(l, i) * u(l, j); + } + }); + }); + return v; + } + +public: + /** + * @brief Solve the multiple right-hand sides linear problem Ax=b or its transposed version A^tx=b inplace. + * + * The solver method is band gaussian elimination with partial pivoting using the LU-factorized matrix A. The implementation is LAPACK method dgbtrs. + * + * @param[in, out] b A 2D Kokkos::View storing the multiple right-hand sides of the problem and receiving the corresponding solution. + * @param transpose Choose between the direct or transposed version of the linear problem. + */ + void solve(MultiRHS b, bool const transpose) const override + { + assert(b.extent(0) == size()); + + auto b_host = create_mirror_view(Kokkos::DefaultHostExecutionSpace(), b); + Kokkos::deep_copy(b_host, b); + int const info = LAPACKE_dgbtrs( + LAPACK_ROW_MAJOR, + transpose ? 'T' : 'N', + b_host.extent(0), + m_kl, + m_ku, + b_host.extent(1), + m_q.data(), + m_q.stride( + 0), // m_q.stride(0) if LAPACK_ROW_MAJOR, m_q.stride(1) if LAPACK_COL_MAJOR + m_ipiv.data(), + b_host.data(), + b_host.stride(0)); + if (info != 0) { + throw std::runtime_error( + "LAPACKE_dgbtrs failed with error code " + std::to_string(info)); + } + Kokkos::deep_copy(b, b_host); + } +}; + +} // namespace ddc::detail From af23572094301bd67229fe9bdd6208b95236e759 Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 29 May 2024 15:48:24 +0200 Subject: [PATCH 090/189] wip --- include/ddc/kernels/splines.hpp | 1 + ... => splines_linear_problem_2x2_blocks.hpp} | 51 ++++++++----------- .../splines/splines_linear_problem_maker.hpp | 41 ++++++++++++++- tests/splines/matrix.cpp | 21 ++++++++ 4 files changed, 82 insertions(+), 32 deletions(-) rename include/ddc/kernels/splines/{splines_linear_problem_corner_block.hpp => splines_linear_problem_2x2_blocks.hpp} (87%) diff --git a/include/ddc/kernels/splines.hpp b/include/ddc/kernels/splines.hpp index 1ea9bd201..c31c4ca90 100644 --- a/include/ddc/kernels/splines.hpp +++ b/include/ddc/kernels/splines.hpp @@ -23,4 +23,5 @@ #include "splines/splines_linear_problem_dense.hpp" #include "splines/splines_linear_problem_maker.hpp" #include "splines/splines_linear_problem_sparse.hpp" +#include "splines/splines_linear_problem_2x2_blocks.hpp" #include "splines/view.hpp" diff --git a/include/ddc/kernels/splines/splines_linear_problem_corner_block.hpp b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp similarity index 87% rename from include/ddc/kernels/splines/splines_linear_problem_corner_block.hpp rename to include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp index 0f9cdf0cc..9c86fd6d9 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_corner_block.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp @@ -45,8 +45,8 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem //------------------------------------- std::shared_ptr m_q_block; std::shared_ptr> m_delta; - Kokkos::View m_Abm_1_gamma; - Kokkos::View m_lambda; + Kokkos::View m_Abm_1_gamma; + Kokkos::View m_lambda; public: /** @@ -144,7 +144,7 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem delta.set_element(i, j, delta.get_element(i, j) - val); }); } - + public: /** * @brief Perform a pre-process operation on the solver. Must be called after filling the matrix. @@ -160,9 +160,7 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem } private: - virtual ddc::DSpan2D_stride solve_lambda_section( - ddc::DSpan2D_stride const v, - ddc::DView2D_stride const u) const + virtual MultiRHS solve_lambda_section(MultiRHS const v, MultiRHS const u) const { auto lambda_device = create_mirror_view_and_copy(ExecSpace(), m_lambda); auto nb_proxy = m_nb; @@ -187,9 +185,7 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem return v; } - virtual ddc::DSpan2D_stride solve_lambda_section_transpose( - ddc::DSpan2D_stride const u, - ddc::DView2D_stride const v) const + virtual MultiRHS solve_lambda_section_transpose(MultiRHS const u, MultiRHS const v) const { auto lambda_device = create_mirror_view_and_copy(ExecSpace(), m_lambda); auto nb_proxy = m_nb; @@ -214,9 +210,7 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem return u; } - virtual ddc::DSpan2D_stride solve_gamma_section( - ddc::DSpan2D_stride const u, - ddc::DView2D_stride const v) const + virtual MultiRHS solve_gamma_section(MultiRHS const u, MultiRHS const v) const { auto Abm_1_gamma_device = create_mirror_view_and_copy(ExecSpace(), m_Abm_1_gamma); auto nb_proxy = m_nb; @@ -241,9 +235,7 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem return u; } - virtual ddc::DSpan2D_stride solve_gamma_section_transpose( - ddc::DSpan2D_stride const v, - ddc::DView2D_stride const u) const + virtual MultiRHS solve_gamma_section_transpose(MultiRHS const v, MultiRHS const u) const { auto Abm_1_gamma_device = create_mirror_view_and_copy(ExecSpace(), m_Abm_1_gamma); auto nb_proxy = m_nb; @@ -283,22 +275,19 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem auto b_host = create_mirror_view(Kokkos::DefaultHostExecutionSpace(), b); Kokkos::deep_copy(b_host, b); - int const info = LAPACKE_dgbtrs( - LAPACK_ROW_MAJOR, - transpose ? 'T' : 'N', - b_host.extent(0), - m_kl, - m_ku, - b_host.extent(1), - m_q.data(), - m_q.stride( - 0), // m_q.stride(0) if LAPACK_ROW_MAJOR, m_q.stride(1) if LAPACK_COL_MAJOR - m_ipiv.data(), - b_host.data(), - b_host.stride(0)); - if (info != 0) { - throw std::runtime_error( - "LAPACKE_dgbtrs failed with error code " + std::to_string(info)); + MultiRHS u = Kokkos::subview(b, std::pair(0, m_nb), Kokkos::ALL); + MultiRHS v = Kokkos:: + subview(b, std::pair(m_nb, b.extent(0)), Kokkos::ALL); + if (!transpose) { + m_q_block->solve_inplace(u); + solve_lambda_section(v, u); + m_delta->solve_inplace(v); + solve_gamma_section(u, v); + } else { + solve_gamma_section_transpose(v, u); + m_delta->solve_transpose_inplace(v); + solve_lambda_section_transpose(u, v); + m_q_block->solve_transpose_inplace(u); } Kokkos::deep_copy(b, b_host); } diff --git a/include/ddc/kernels/splines/splines_linear_problem_maker.hpp b/include/ddc/kernels/splines/splines_linear_problem_maker.hpp index b6774522b..0af8cbf3c 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_maker.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_maker.hpp @@ -7,6 +7,7 @@ #include #include +#include "splines_linear_problem_2x2_blocks.hpp" #include "splines_linear_problem_band.hpp" #include "splines_linear_problem_dense.hpp" #include "splines_linear_problem_sparse.hpp" @@ -50,13 +51,51 @@ class SplinesLinearProblemMaker int const ku, [[maybe_unused]] bool const pds) { - if (2 * kl + 1 + ku >= n) { + if (2 * kl + ku + 1 >= n) { return std::make_unique>(n); } else { return std::make_unique>(n, kl, ku); } } + /** + * @brief Construct a 2x2-blocks with band top-left block matrix + * + * @tparam the Kokkos::ExecutionSpace on which matrix-related operation will be performed. + * @param n The size of one of the dimensions of the square matrix. + * @param kl The number of subdiagonals. + * @param ku The number of superdiagonals. + * @param pds A boolean indicating if the matrix is positive-definite symetric or not. + * + * @return The SplinesLinearProblem instance. + */ + template + static std::unique_ptr> make_new_2x2_blocks_with_band_top_left( + int const n, + int const kl, + int const ku, + bool const pds, + int const block1_size, + int const block2_size = 0) + { + assert(block2_size + == 0); // block2_size is a placeholder while SplinesLinearProblem3x3Blocks is not implemented. + + // TODO: clarify if top-left or bottom_right is the band + + int const top_left_size = n - block1_size - block2_size; + std::unique_ptr> top_left_block + = make_new_band(top_left_size, kl, ku, pds); + if (block2_size == 0) { + return std::make_unique>(n, block1_size, std::move(top_left_block)); + } else { + /* + return std::make_unique>(n, block1_size, block2_size, std::move(block_mat)); +*/ + } + } /** * @brief Construct a sparse matrix * diff --git a/tests/splines/matrix.cpp b/tests/splines/matrix.cpp index 3f86e6e09..085486d07 100644 --- a/tests/splines/matrix.cpp +++ b/tests/splines/matrix.cpp @@ -248,6 +248,27 @@ TEST_P(MatrixSizesFixture, OffsetBanded) solve_and_validate(*matrix); } +TEST_P(MatrixSizesFixture, 2x2Blocks) +{ + auto const [N, k] = GetParam(); + std::unique_ptr> matrix + = ddc::detail::SplinesLinearProblemMaker::make_new_2x2_blocks_with_band_top_left< + Kokkos::DefaultExecutionSpace>(N, k, k, false, 3); + + // Build a non-symmetric full-rank band matrix + for (std::size_t i(0); i < N; ++i) { + matrix->set_element(i, i, 3. / 4 * ((N + 1) * i + 1)); + for (std::size_t j(std::max(0, int(i) - int(k))); j < i; ++j) { + matrix->set_element(i, j, -(1. / 4) / k * (N * i + j + 1)); + } + for (std::size_t j(i + 1); j < std::min(N, i + k + 1); ++j) { + matrix->set_element(i, j, -(1. / 4) / k * (N * i + j + 1)); + } + } + + solve_and_validate(*matrix); +} + TEST_P(MatrixSizesFixture, Sparse) { auto const [N, k] = GetParam(); From 4a714bd5b164a55859219b0e2cb44de6c1815d46 Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 29 May 2024 16:48:46 +0200 Subject: [PATCH 091/189] runs but wrong result --- .../splines_linear_problem_2x2_blocks.hpp | 39 ++++++++++++------- .../splines/splines_linear_problem_maker.hpp | 2 +- 2 files changed, 27 insertions(+), 14 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp index 9c86fd6d9..d5822c695 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp @@ -15,6 +15,7 @@ #endif #include "splines_linear_problem.hpp" +#include "splines_linear_problem_dense.hpp" namespace ddc::detail { @@ -43,8 +44,8 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem // | lambda | delta | // //------------------------------------- - std::shared_ptr m_q_block; - std::shared_ptr> m_delta; + std::shared_ptr> m_q_block; + std::shared_ptr> m_delta; Kokkos::View m_Abm_1_gamma; Kokkos::View m_lambda; @@ -62,7 +63,7 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem , m_k(k) , m_nb(mat_size - k) , m_q_block(std::move(q)) - , m_delta(new SplinesLinearSolver(k)) + , m_delta(new SplinesLinearProblemDense(k)) , m_Abm_1_gamma("Abm_1_gamma", m_nb, m_k) , m_lambda("lambda", m_k, m_nb) { @@ -75,7 +76,7 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem protected: explicit SplinesLinearProblem2x2Blocks( - std::size_t const n, + std::size_t const mat_size, std::size_t const k, std::unique_ptr> q, std::size_t const lambda_size1, @@ -84,7 +85,7 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem , m_k(k) , m_nb(mat_size - k) , m_q_block(std::move(q)) - , m_delta(new MatrixDense(k)) + , m_delta(new SplinesLinearProblemDense(k)) , m_Abm_1_gamma("Abm_1_gamma", m_nb, m_k) , m_lambda("lambda", lambda_size1, lambda_size2) { @@ -141,7 +142,7 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem for (int l = 0; l < m_nb; ++l) { val += m_lambda(i, l) * m_Abm_1_gamma(l, j); } - delta.set_element(i, j, delta.get_element(i, j) - val); + m_delta->set_element(i, j, m_delta->get_element(i, j) - val); }); } @@ -154,12 +155,16 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem void setup_solver() override { m_q_block->setup_solver(); - m_q_block->solve_inplace(m_Abm_1_gamma); + auto Abm_1_gamma_device = create_mirror_view_and_copy(ExecSpace(), m_Abm_1_gamma); + m_q_block->solve(Abm_1_gamma_device); + deep_copy(m_Abm_1_gamma, Abm_1_gamma_device); calculate_delta_to_factorize(); m_delta->setup_solver(); } -private: + /** + * [SHOULD BE PRIVATE (GPU programming limitation)] + */ virtual MultiRHS solve_lambda_section(MultiRHS const v, MultiRHS const u) const { auto lambda_device = create_mirror_view_and_copy(ExecSpace(), m_lambda); @@ -185,6 +190,9 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem return v; } + /** + * [SHOULD BE PRIVATE (GPU programming limitation)] + */ virtual MultiRHS solve_lambda_section_transpose(MultiRHS const u, MultiRHS const v) const { auto lambda_device = create_mirror_view_and_copy(ExecSpace(), m_lambda); @@ -210,6 +218,9 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem return u; } + /** + * [SHOULD BE PRIVATE (GPU programming limitation)] + */ virtual MultiRHS solve_gamma_section(MultiRHS const u, MultiRHS const v) const { auto Abm_1_gamma_device = create_mirror_view_and_copy(ExecSpace(), m_Abm_1_gamma); @@ -235,6 +246,9 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem return u; } + /** + * [SHOULD BE PRIVATE (GPU programming limitation)] + */ virtual MultiRHS solve_gamma_section_transpose(MultiRHS const v, MultiRHS const u) const { auto Abm_1_gamma_device = create_mirror_view_and_copy(ExecSpace(), m_Abm_1_gamma); @@ -260,7 +274,6 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem return v; } -public: /** * @brief Solve the multiple right-hand sides linear problem Ax=b or its transposed version A^tx=b inplace. * @@ -279,15 +292,15 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem MultiRHS v = Kokkos:: subview(b, std::pair(m_nb, b.extent(0)), Kokkos::ALL); if (!transpose) { - m_q_block->solve_inplace(u); + m_q_block->solve(u); solve_lambda_section(v, u); - m_delta->solve_inplace(v); + m_delta->solve(v); solve_gamma_section(u, v); } else { solve_gamma_section_transpose(v, u); - m_delta->solve_transpose_inplace(v); + m_delta->solve(v, true); solve_lambda_section_transpose(u, v); - m_q_block->solve_transpose_inplace(u); + m_q_block->solve(u, true); } Kokkos::deep_copy(b, b_host); } diff --git a/include/ddc/kernels/splines/splines_linear_problem_maker.hpp b/include/ddc/kernels/splines/splines_linear_problem_maker.hpp index 85739ec3c..d02cf14a2 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_maker.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_maker.hpp @@ -88,7 +88,7 @@ class SplinesLinearProblemMaker int const top_left_size = n - block1_size - block2_size; std::unique_ptr> top_left_block - = make_new_band(top_left_size, kl, ku, pds); + = make_new_band(top_left_size, kl, ku, pds); if (block2_size == 0) { return std::make_unique>(n, block1_size, std::move(top_left_block)); From 17062e1de7db26ae0a86b0ccd649873acb04a931 Mon Sep 17 00:00:00 2001 From: blegouix Date: Thu, 30 May 2024 09:11:52 +0200 Subject: [PATCH 092/189] fix --- include/ddc/kernels/splines.hpp | 2 +- .../splines/splines_linear_problem_2x2_blocks.hpp | 15 ++++----------- 2 files changed, 5 insertions(+), 12 deletions(-) diff --git a/include/ddc/kernels/splines.hpp b/include/ddc/kernels/splines.hpp index b6f2d6c51..5a76d29ed 100644 --- a/include/ddc/kernels/splines.hpp +++ b/include/ddc/kernels/splines.hpp @@ -19,10 +19,10 @@ #include "splines/spline_evaluator.hpp" #include "splines/spline_evaluator_2d.hpp" #include "splines/splines_linear_problem.hpp" +#include "splines/splines_linear_problem_2x2_blocks.hpp" #include "splines/splines_linear_problem_band.hpp" #include "splines/splines_linear_problem_dense.hpp" #include "splines/splines_linear_problem_maker.hpp" #include "splines/splines_linear_problem_pds_band.hpp" #include "splines/splines_linear_problem_sparse.hpp" -#include "splines/splines_linear_problem_2x2_blocks.hpp" #include "splines/view.hpp" diff --git a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp index d5822c695..f7e8a2fee 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp @@ -165,7 +165,7 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem /** * [SHOULD BE PRIVATE (GPU programming limitation)] */ - virtual MultiRHS solve_lambda_section(MultiRHS const v, MultiRHS const u) const + virtual void solve_lambda_section(MultiRHS const v, MultiRHS const u) const { auto lambda_device = create_mirror_view_and_copy(ExecSpace(), m_lambda); auto nb_proxy = m_nb; @@ -187,13 +187,12 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem } }); }); - return v; } /** * [SHOULD BE PRIVATE (GPU programming limitation)] */ - virtual MultiRHS solve_lambda_section_transpose(MultiRHS const u, MultiRHS const v) const + virtual void solve_lambda_section_transpose(MultiRHS const u, MultiRHS const v) const { auto lambda_device = create_mirror_view_and_copy(ExecSpace(), m_lambda); auto nb_proxy = m_nb; @@ -215,13 +214,12 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem } }); }); - return u; } /** * [SHOULD BE PRIVATE (GPU programming limitation)] */ - virtual MultiRHS solve_gamma_section(MultiRHS const u, MultiRHS const v) const + virtual void solve_gamma_section(MultiRHS const u, MultiRHS const v) const { auto Abm_1_gamma_device = create_mirror_view_and_copy(ExecSpace(), m_Abm_1_gamma); auto nb_proxy = m_nb; @@ -243,13 +241,12 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem } }); }); - return u; } /** * [SHOULD BE PRIVATE (GPU programming limitation)] */ - virtual MultiRHS solve_gamma_section_transpose(MultiRHS const v, MultiRHS const u) const + virtual void solve_gamma_section_transpose(MultiRHS const v, MultiRHS const u) const { auto Abm_1_gamma_device = create_mirror_view_and_copy(ExecSpace(), m_Abm_1_gamma); auto nb_proxy = m_nb; @@ -271,7 +268,6 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem } }); }); - return v; } /** @@ -286,8 +282,6 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem { assert(b.extent(0) == size()); - auto b_host = create_mirror_view(Kokkos::DefaultHostExecutionSpace(), b); - Kokkos::deep_copy(b_host, b); MultiRHS u = Kokkos::subview(b, std::pair(0, m_nb), Kokkos::ALL); MultiRHS v = Kokkos:: subview(b, std::pair(m_nb, b.extent(0)), Kokkos::ALL); @@ -302,7 +296,6 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem solve_lambda_section_transpose(u, v); m_q_block->solve(u, true); } - Kokkos::deep_copy(b, b_host); } }; From 769da52264a8a8030adb5337c6f1c865ea12f04c Mon Sep 17 00:00:00 2001 From: blegouix Date: Thu, 30 May 2024 09:54:22 +0200 Subject: [PATCH 093/189] rely on Kokkos::View to store nb and k --- .../splines_linear_problem_2x2_blocks.hpp | 79 ++++++++----------- 1 file changed, 34 insertions(+), 45 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp index f7e8a2fee..9b1a1efb8 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp @@ -36,8 +36,6 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem using SplinesLinearProblem::size; protected: - std::size_t const m_k; // small block size - std::size_t const m_nb; // main block matrix size //------------------------------------- // // q = | q_block | gamma | @@ -60,15 +58,12 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem std::size_t const k, std::unique_ptr> q) : SplinesLinearProblem(mat_size) - , m_k(k) - , m_nb(mat_size - k) , m_q_block(std::move(q)) , m_delta(new SplinesLinearProblemDense(k)) - , m_Abm_1_gamma("Abm_1_gamma", m_nb, m_k) - , m_lambda("lambda", m_k, m_nb) + , m_Abm_1_gamma("Abm_1_gamma", m_q_block->size(), mat_size - m_q_block->size()) + , m_lambda("lambda", mat_size - m_q_block->size(), m_q_block->size()) { - assert(m_k <= mat_size); - assert(m_nb == m_q_block->size()); // TODO: remove + assert(m_q_block->size() <= mat_size); Kokkos::deep_copy(m_Abm_1_gamma, 0.); Kokkos::deep_copy(m_lambda, 0.); @@ -82,15 +77,12 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem std::size_t const lambda_size1, std::size_t const lambda_size2) : SplinesLinearProblem(mat_size) - , m_k(k) - , m_nb(mat_size - k) , m_q_block(std::move(q)) , m_delta(new SplinesLinearProblemDense(k)) - , m_Abm_1_gamma("Abm_1_gamma", m_nb, m_k) + , m_Abm_1_gamma("Abm_1_gamma", m_q_block->size(), mat_size - m_q_block->size()) , m_lambda("lambda", lambda_size1, lambda_size2) { - assert(m_k <= mat_size); - assert(m_nb == m_q_block->size()); // TODO: remove + assert(m_q_block->size() <= mat_size); Kokkos::deep_copy(m_Abm_1_gamma, 0.); Kokkos::deep_copy(m_lambda, 0.); @@ -102,14 +94,15 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem assert(i < size()); assert(j < size()); - if (i < m_nb && j < m_nb) { + std::size_t const nq = m_q_block->size(); + if (i < nq && j < nq) { return m_q_block->get_element(i, j); - } else if (i >= m_nb && j >= m_nb) { - return m_delta->get_element(i - m_nb, j - m_nb); - } else if (j >= m_nb) { - return m_Abm_1_gamma(i, j - m_nb); + } else if (i >= nq && j >= nq) { + return m_delta->get_element(i - nq, j - nq); + } else if (j >= nq) { + return m_Abm_1_gamma(i, j - nq); } else { - return m_lambda(i - m_nb, j); + return m_lambda(i - nq, j); } } @@ -118,14 +111,15 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem assert(i < size()); assert(j < size()); - if (i < m_nb && j < m_nb) { + std::size_t const nq = m_q_block->size(); + if (i < nq && j < nq) { m_q_block->set_element(i, j, aij); - } else if (i >= m_nb && j >= m_nb) { - m_delta->set_element(i - m_nb, j - m_nb, aij); - } else if (j >= m_nb) { - m_Abm_1_gamma(i, j - m_nb) = aij; + } else if (i >= nq && j >= nq) { + m_delta->set_element(i - nq, j - nq, aij); + } else if (j >= nq) { + m_Abm_1_gamma(i, j - nq) = aij; } else { - m_lambda(i - m_nb, j) = aij; + m_lambda(i - nq, j) = aij; } } @@ -136,10 +130,10 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem "calculate_delta_to_factorize", Kokkos::MDRangePolicy< Kokkos::DefaultHostExecutionSpace, - Kokkos::Rank<2>>({0, 0}, {m_k, m_k}), + Kokkos::Rank<2>>({0, 0}, {m_delta->size(), m_delta->size()}), [&](const int i, const int j) { double val = 0.0; - for (int l = 0; l < m_nb; ++l) { + for (int l = 0; l < m_q_block->size(); ++l) { val += m_lambda(i, l) * m_Abm_1_gamma(l, j); } m_delta->set_element(i, j, m_delta->get_element(i, j) - val); @@ -168,8 +162,6 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem virtual void solve_lambda_section(MultiRHS const v, MultiRHS const u) const { auto lambda_device = create_mirror_view_and_copy(ExecSpace(), m_lambda); - auto nb_proxy = m_nb; - auto k_proxy = m_k; Kokkos::parallel_for( "solve_lambda_section", Kokkos::TeamPolicy(v.extent(1), Kokkos::AUTO), @@ -179,10 +171,10 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem Kokkos::parallel_for( - Kokkos::TeamThreadRange(teamMember, k_proxy), + Kokkos::TeamThreadRange(teamMember, v.extent(0)), [&](const int i) { // Upper diagonals in lambda - for (int l = 0; l < nb_proxy; ++l) { + for (int l = 0; l < u.extent(0); ++l) { v(i, j) -= lambda_device(i, l) * u(l, j); } }); @@ -195,8 +187,6 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem virtual void solve_lambda_section_transpose(MultiRHS const u, MultiRHS const v) const { auto lambda_device = create_mirror_view_and_copy(ExecSpace(), m_lambda); - auto nb_proxy = m_nb; - auto k_proxy = m_k; Kokkos::parallel_for( "solve_lambda_section_transpose", Kokkos::TeamPolicy(u.extent(1), Kokkos::AUTO), @@ -206,10 +196,10 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem Kokkos::parallel_for( - Kokkos::TeamThreadRange(teamMember, nb_proxy), + Kokkos::TeamThreadRange(teamMember, u.extent(0)), [&](const int i) { // Upper diagonals in lambda - for (int l = 0; l < k_proxy; ++l) { + for (int l = 0; l < v.extent(0); ++l) { u(i, j) -= lambda_device(l, i) * v(l, j); } }); @@ -222,8 +212,6 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem virtual void solve_gamma_section(MultiRHS const u, MultiRHS const v) const { auto Abm_1_gamma_device = create_mirror_view_and_copy(ExecSpace(), m_Abm_1_gamma); - auto nb_proxy = m_nb; - auto k_proxy = m_k; Kokkos::parallel_for( "solve_gamma_section", Kokkos::TeamPolicy(u.extent(1), Kokkos::AUTO), @@ -233,10 +221,10 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem Kokkos::parallel_for( - Kokkos::TeamThreadRange(teamMember, nb_proxy), + Kokkos::TeamThreadRange(teamMember, u.extent(0)), [&](const int i) { // Upper diagonals in lambda - for (int l = 0; l < k_proxy; ++l) { + for (int l = 0; l < v.extent(0); ++l) { u(i, j) -= Abm_1_gamma_device(i, l) * v(l, j); } }); @@ -249,8 +237,6 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem virtual void solve_gamma_section_transpose(MultiRHS const v, MultiRHS const u) const { auto Abm_1_gamma_device = create_mirror_view_and_copy(ExecSpace(), m_Abm_1_gamma); - auto nb_proxy = m_nb; - auto k_proxy = m_k; Kokkos::parallel_for( "solve_gamma_section_transpose", Kokkos::TeamPolicy(v.extent(1), Kokkos::AUTO), @@ -260,10 +246,10 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem Kokkos::parallel_for( - Kokkos::TeamThreadRange(teamMember, k_proxy), + Kokkos::TeamThreadRange(teamMember, v.extent(0)), [&](const int i) { // Upper diagonals in lambda - for (int l = 0; l < nb_proxy; ++l) { + for (int l = 0; l < u.extent(0); ++l) { v(i, j) -= Abm_1_gamma_device(l, i) * u(l, j); } }); @@ -282,9 +268,12 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem { assert(b.extent(0) == size()); - MultiRHS u = Kokkos::subview(b, std::pair(0, m_nb), Kokkos::ALL); + MultiRHS u = Kokkos:: + subview(b, std::pair(0, m_q_block->size()), Kokkos::ALL); MultiRHS v = Kokkos:: - subview(b, std::pair(m_nb, b.extent(0)), Kokkos::ALL); + subview(b, + std::pair(m_q_block->size(), b.extent(0)), + Kokkos::ALL); if (!transpose) { m_q_block->solve(u); solve_lambda_section(v, u); From fdbfecf284f452f6d38f6569df1b7ca0422e77af Mon Sep 17 00:00:00 2001 From: blegouix Date: Thu, 30 May 2024 10:03:41 +0200 Subject: [PATCH 094/189] renaming --- .../splines_linear_problem_2x2_blocks.hpp | 168 ++++++++++-------- 1 file changed, 91 insertions(+), 77 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp index 9b1a1efb8..5e767f07c 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp @@ -22,7 +22,7 @@ namespace ddc::detail { /** * @brief A 2x2-blocks linear problem dedicated to the computation of a spline approximation, with all blocks except top-left being stored in dense format. * - * The storage format is dense row-major for top-left and bottom-right blocks, the one of SplinesLinearProblemDense (which is also dense row-major in practice) for bottom-right block and undefined for the top-left one (determined by the type of q_block). + * The storage format is dense row-major for top-left and bottom-right blocks, the one of SplinesLinearProblemDense (which is also dense row-major in practice) for bottom-right block and undefined for the top-left one (determined by the type of top_left_block). * * This class implements a Schur complement method to perform a block-LU factorization and solve, calling tl_block and br_block setup_solver() and solve() methods for internal operations. * @@ -38,14 +38,14 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem protected: //------------------------------------- // - // q = | q_block | gamma | - // | lambda | delta | + // q = | top_left_block | top_right_block | + // | bottom_left_block | bottom_right_block | // //------------------------------------- - std::shared_ptr> m_q_block; - std::shared_ptr> m_delta; - Kokkos::View m_Abm_1_gamma; - Kokkos::View m_lambda; + std::shared_ptr> m_top_left_block; + std::shared_ptr> m_bottom_right_block; + Kokkos::View m_top_right_block; + Kokkos::View m_bottom_left_block; public: /** @@ -58,15 +58,21 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem std::size_t const k, std::unique_ptr> q) : SplinesLinearProblem(mat_size) - , m_q_block(std::move(q)) - , m_delta(new SplinesLinearProblemDense(k)) - , m_Abm_1_gamma("Abm_1_gamma", m_q_block->size(), mat_size - m_q_block->size()) - , m_lambda("lambda", mat_size - m_q_block->size(), m_q_block->size()) + , m_top_left_block(std::move(q)) + , m_bottom_right_block(new SplinesLinearProblemDense(k)) + , m_top_right_block( + "top_right_block", + m_top_left_block->size(), + mat_size - m_top_left_block->size()) + , m_bottom_left_block( + "bottom_left_block", + mat_size - m_top_left_block->size(), + m_top_left_block->size()) { - assert(m_q_block->size() <= mat_size); + assert(m_top_left_block->size() <= mat_size); - Kokkos::deep_copy(m_Abm_1_gamma, 0.); - Kokkos::deep_copy(m_lambda, 0.); + Kokkos::deep_copy(m_top_right_block, 0.); + Kokkos::deep_copy(m_bottom_left_block, 0.); } protected: @@ -74,18 +80,21 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem std::size_t const mat_size, std::size_t const k, std::unique_ptr> q, - std::size_t const lambda_size1, - std::size_t const lambda_size2) + std::size_t const bottom_left_block_size1, + std::size_t const bottom_left_block_size2) : SplinesLinearProblem(mat_size) - , m_q_block(std::move(q)) - , m_delta(new SplinesLinearProblemDense(k)) - , m_Abm_1_gamma("Abm_1_gamma", m_q_block->size(), mat_size - m_q_block->size()) - , m_lambda("lambda", lambda_size1, lambda_size2) + , m_top_left_block(std::move(q)) + , m_bottom_right_block(new SplinesLinearProblemDense(k)) + , m_top_right_block( + "top_right_block", + m_top_left_block->size(), + mat_size - m_top_left_block->size()) + , m_bottom_left_block("bottom_left_block", bottom_left_block_size1, bottom_left_block_size2) { - assert(m_q_block->size() <= mat_size); + assert(m_top_left_block->size() <= mat_size); - Kokkos::deep_copy(m_Abm_1_gamma, 0.); - Kokkos::deep_copy(m_lambda, 0.); + Kokkos::deep_copy(m_top_right_block, 0.); + Kokkos::deep_copy(m_bottom_left_block, 0.); } public: @@ -94,15 +103,15 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem assert(i < size()); assert(j < size()); - std::size_t const nq = m_q_block->size(); + std::size_t const nq = m_top_left_block->size(); if (i < nq && j < nq) { - return m_q_block->get_element(i, j); + return m_top_left_block->get_element(i, j); } else if (i >= nq && j >= nq) { - return m_delta->get_element(i - nq, j - nq); + return m_bottom_right_block->get_element(i - nq, j - nq); } else if (j >= nq) { - return m_Abm_1_gamma(i, j - nq); + return m_top_right_block(i, j - nq); } else { - return m_lambda(i - nq, j); + return m_bottom_left_block(i - nq, j); } } @@ -111,32 +120,33 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem assert(i < size()); assert(j < size()); - std::size_t const nq = m_q_block->size(); + std::size_t const nq = m_top_left_block->size(); if (i < nq && j < nq) { - m_q_block->set_element(i, j, aij); + m_top_left_block->set_element(i, j, aij); } else if (i >= nq && j >= nq) { - m_delta->set_element(i - nq, j - nq, aij); + m_bottom_right_block->set_element(i - nq, j - nq, aij); } else if (j >= nq) { - m_Abm_1_gamma(i, j - nq) = aij; + m_top_right_block(i, j - nq) = aij; } else { - m_lambda(i - nq, j) = aij; + m_bottom_left_block(i - nq, j) = aij; } } private: - virtual void calculate_delta_to_factorize() + virtual void calculate_bottom_right_block_to_factorize() { Kokkos::parallel_for( - "calculate_delta_to_factorize", - Kokkos::MDRangePolicy< - Kokkos::DefaultHostExecutionSpace, - Kokkos::Rank<2>>({0, 0}, {m_delta->size(), m_delta->size()}), + "calculate_bottom_right_block_to_factorize", + Kokkos::MDRangePolicy>( + {0, 0}, + {m_bottom_right_block->size(), m_bottom_right_block->size()}), [&](const int i, const int j) { double val = 0.0; - for (int l = 0; l < m_q_block->size(); ++l) { - val += m_lambda(i, l) * m_Abm_1_gamma(l, j); + for (int l = 0; l < m_top_left_block->size(); ++l) { + val += m_bottom_left_block(i, l) * m_top_right_block(l, j); } - m_delta->set_element(i, j, m_delta->get_element(i, j) - val); + m_bottom_right_block + ->set_element(i, j, m_bottom_right_block->get_element(i, j) - val); }); } @@ -148,22 +158,23 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem */ void setup_solver() override { - m_q_block->setup_solver(); - auto Abm_1_gamma_device = create_mirror_view_and_copy(ExecSpace(), m_Abm_1_gamma); - m_q_block->solve(Abm_1_gamma_device); - deep_copy(m_Abm_1_gamma, Abm_1_gamma_device); - calculate_delta_to_factorize(); - m_delta->setup_solver(); + m_top_left_block->setup_solver(); + auto top_right_block_device = create_mirror_view_and_copy(ExecSpace(), m_top_right_block); + m_top_left_block->solve(top_right_block_device); + deep_copy(m_top_right_block, top_right_block_device); + calculate_bottom_right_block_to_factorize(); + m_bottom_right_block->setup_solver(); } /** * [SHOULD BE PRIVATE (GPU programming limitation)] */ - virtual void solve_lambda_section(MultiRHS const v, MultiRHS const u) const + virtual void solve_bottom_left_block_section(MultiRHS const v, MultiRHS const u) const { - auto lambda_device = create_mirror_view_and_copy(ExecSpace(), m_lambda); + auto bottom_left_block_device + = create_mirror_view_and_copy(ExecSpace(), m_bottom_left_block); Kokkos::parallel_for( - "solve_lambda_section", + "solve_bottom_left_block_section", Kokkos::TeamPolicy(v.extent(1), Kokkos::AUTO), KOKKOS_LAMBDA( const typename Kokkos::TeamPolicy::member_type& teamMember) { @@ -173,9 +184,9 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem Kokkos::parallel_for( Kokkos::TeamThreadRange(teamMember, v.extent(0)), [&](const int i) { - // Upper diagonals in lambda + // Upper diagonals in bottom_left_block for (int l = 0; l < u.extent(0); ++l) { - v(i, j) -= lambda_device(i, l) * u(l, j); + v(i, j) -= bottom_left_block_device(i, l) * u(l, j); } }); }); @@ -184,11 +195,12 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem /** * [SHOULD BE PRIVATE (GPU programming limitation)] */ - virtual void solve_lambda_section_transpose(MultiRHS const u, MultiRHS const v) const + virtual void solve_bottom_left_block_section_transpose(MultiRHS const u, MultiRHS const v) const { - auto lambda_device = create_mirror_view_and_copy(ExecSpace(), m_lambda); + auto bottom_left_block_device + = create_mirror_view_and_copy(ExecSpace(), m_bottom_left_block); Kokkos::parallel_for( - "solve_lambda_section_transpose", + "solve_bottom_left_block_section_transpose", Kokkos::TeamPolicy(u.extent(1), Kokkos::AUTO), KOKKOS_LAMBDA( const typename Kokkos::TeamPolicy::member_type& teamMember) { @@ -198,9 +210,9 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem Kokkos::parallel_for( Kokkos::TeamThreadRange(teamMember, u.extent(0)), [&](const int i) { - // Upper diagonals in lambda + // Upper diagonals in bottom_left_block for (int l = 0; l < v.extent(0); ++l) { - u(i, j) -= lambda_device(l, i) * v(l, j); + u(i, j) -= bottom_left_block_device(l, i) * v(l, j); } }); }); @@ -209,11 +221,11 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem /** * [SHOULD BE PRIVATE (GPU programming limitation)] */ - virtual void solve_gamma_section(MultiRHS const u, MultiRHS const v) const + virtual void solve_top_right_block_section(MultiRHS const u, MultiRHS const v) const { - auto Abm_1_gamma_device = create_mirror_view_and_copy(ExecSpace(), m_Abm_1_gamma); + auto top_right_block_device = create_mirror_view_and_copy(ExecSpace(), m_top_right_block); Kokkos::parallel_for( - "solve_gamma_section", + "solve_top_right_block_section", Kokkos::TeamPolicy(u.extent(1), Kokkos::AUTO), KOKKOS_LAMBDA( const typename Kokkos::TeamPolicy::member_type& teamMember) { @@ -223,9 +235,9 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem Kokkos::parallel_for( Kokkos::TeamThreadRange(teamMember, u.extent(0)), [&](const int i) { - // Upper diagonals in lambda + // Upper diagonals in bottom_left_block for (int l = 0; l < v.extent(0); ++l) { - u(i, j) -= Abm_1_gamma_device(i, l) * v(l, j); + u(i, j) -= top_right_block_device(i, l) * v(l, j); } }); }); @@ -234,11 +246,11 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem /** * [SHOULD BE PRIVATE (GPU programming limitation)] */ - virtual void solve_gamma_section_transpose(MultiRHS const v, MultiRHS const u) const + virtual void solve_top_right_block_section_transpose(MultiRHS const v, MultiRHS const u) const { - auto Abm_1_gamma_device = create_mirror_view_and_copy(ExecSpace(), m_Abm_1_gamma); + auto top_right_block_device = create_mirror_view_and_copy(ExecSpace(), m_top_right_block); Kokkos::parallel_for( - "solve_gamma_section_transpose", + "solve_top_right_block_section_transpose", Kokkos::TeamPolicy(v.extent(1), Kokkos::AUTO), KOKKOS_LAMBDA( const typename Kokkos::TeamPolicy::member_type& teamMember) { @@ -248,9 +260,9 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem Kokkos::parallel_for( Kokkos::TeamThreadRange(teamMember, v.extent(0)), [&](const int i) { - // Upper diagonals in lambda + // Upper diagonals in bottom_left_block for (int l = 0; l < u.extent(0); ++l) { - v(i, j) -= Abm_1_gamma_device(l, i) * u(l, j); + v(i, j) -= top_right_block_device(l, i) * u(l, j); } }); }); @@ -269,21 +281,23 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem assert(b.extent(0) == size()); MultiRHS u = Kokkos:: - subview(b, std::pair(0, m_q_block->size()), Kokkos::ALL); + subview(b, + std::pair(0, m_top_left_block->size()), + Kokkos::ALL); MultiRHS v = Kokkos:: subview(b, - std::pair(m_q_block->size(), b.extent(0)), + std::pair(m_top_left_block->size(), b.extent(0)), Kokkos::ALL); if (!transpose) { - m_q_block->solve(u); - solve_lambda_section(v, u); - m_delta->solve(v); - solve_gamma_section(u, v); + m_top_left_block->solve(u); + solve_bottom_left_block_section(v, u); + m_bottom_right_block->solve(v); + solve_top_right_block_section(u, v); } else { - solve_gamma_section_transpose(v, u); - m_delta->solve(v, true); - solve_lambda_section_transpose(u, v); - m_q_block->solve(u, true); + solve_top_right_block_section_transpose(v, u); + m_bottom_right_block->solve(v, true); + solve_bottom_left_block_section_transpose(u, v); + m_top_left_block->solve(u, true); } } }; From 1d4a8ed13c2bfe82a35c50835a81bac41b5b6330 Mon Sep 17 00:00:00 2001 From: blegouix Date: Thu, 30 May 2024 11:10:48 +0200 Subject: [PATCH 095/189] misc --- .../splines_linear_problem_2x2_blocks.hpp | 41 ++++++++++++------- .../splines/splines_linear_problem_maker.hpp | 12 ++---- 2 files changed, 29 insertions(+), 24 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp index 5e767f07c..77fc98d5c 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp @@ -36,16 +36,14 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem using SplinesLinearProblem::size; protected: - //------------------------------------- - // - // q = | top_left_block | top_right_block | - // | bottom_left_block | bottom_right_block | - // - //------------------------------------- + /* + * A = | Q | gamma | + * | lambda | delta | + */ std::shared_ptr> m_top_left_block; - std::shared_ptr> m_bottom_right_block; Kokkos::View m_top_right_block; Kokkos::View m_bottom_left_block; + std::shared_ptr> m_bottom_right_block; public: /** @@ -55,11 +53,9 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem */ explicit SplinesLinearProblem2x2Blocks( std::size_t const mat_size, - std::size_t const k, std::unique_ptr> q) : SplinesLinearProblem(mat_size) , m_top_left_block(std::move(q)) - , m_bottom_right_block(new SplinesLinearProblemDense(k)) , m_top_right_block( "top_right_block", m_top_left_block->size(), @@ -68,6 +64,8 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem "bottom_left_block", mat_size - m_top_left_block->size(), m_top_left_block->size()) + , m_bottom_right_block( + new SplinesLinearProblemDense(mat_size - m_top_left_block->size())) { assert(m_top_left_block->size() <= mat_size); @@ -78,18 +76,18 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem protected: explicit SplinesLinearProblem2x2Blocks( std::size_t const mat_size, - std::size_t const k, std::unique_ptr> q, std::size_t const bottom_left_block_size1, std::size_t const bottom_left_block_size2) : SplinesLinearProblem(mat_size) , m_top_left_block(std::move(q)) - , m_bottom_right_block(new SplinesLinearProblemDense(k)) , m_top_right_block( "top_right_block", m_top_left_block->size(), mat_size - m_top_left_block->size()) , m_bottom_left_block("bottom_left_block", bottom_left_block_size1, bottom_left_block_size2) + , m_bottom_right_block( + new SplinesLinearProblemDense(mat_size - m_top_left_block->size())) { assert(m_top_left_block->size() <= mat_size); @@ -133,10 +131,10 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem } private: - virtual void calculate_bottom_right_block_to_factorize() + virtual void compute_schur_complement() { Kokkos::parallel_for( - "calculate_bottom_right_block_to_factorize", + "compute_schur_complement", Kokkos::MDRangePolicy>( {0, 0}, {m_bottom_right_block->size(), m_bottom_right_block->size()}), @@ -154,15 +152,28 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem /** * @brief Perform a pre-process operation on the solver. Must be called after filling the matrix. * - * Block-LU factorize the matrix A according to the Schur complement method. + * Block-LU factorize the matrix A according to the Schur complement method. The block-LU factorization is: + * + * A = | Q | 0 | | I | Q^-1*gamma | + * | lambda | delta - lambda*Q^-1*gamma | | 0 | I | + * + * So we perform the factorization inplace to store only the relevant blocks in the matrix (while factorizing + * the blocks themselves): + * | Q | Q^-1*gamma | + * | lambda | delta - lambda*Q^-1*gamma | */ void setup_solver() override { m_top_left_block->setup_solver(); + + // Compute Q^-1*gamma auto top_right_block_device = create_mirror_view_and_copy(ExecSpace(), m_top_right_block); m_top_left_block->solve(top_right_block_device); deep_copy(m_top_right_block, top_right_block_device); - calculate_bottom_right_block_to_factorize(); + + // Compute delta - lambda*Q^-1*gamma + compute_schur_complement(); + m_bottom_right_block->setup_solver(); } diff --git a/include/ddc/kernels/splines/splines_linear_problem_maker.hpp b/include/ddc/kernels/splines/splines_linear_problem_maker.hpp index d02cf14a2..fc2af59b7 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_maker.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_maker.hpp @@ -89,16 +89,10 @@ class SplinesLinearProblemMaker int const top_left_size = n - block1_size - block2_size; std::unique_ptr> top_left_block = make_new_band(top_left_size, kl, ku, pds); - if (block2_size == 0) { - return std::make_unique>(n, block1_size, std::move(top_left_block)); - } else { - /* - return std::make_unique>(n, block1_size, block2_size, std::move(block_mat)); -*/ - } + return std::make_unique< + SplinesLinearProblem2x2Blocks>(n, std::move(top_left_block)); } + /** * @brief Construct a sparse matrix * From 68b826fdf53d878bff26a5b2112b15f0400543fa Mon Sep 17 00:00:00 2001 From: blegouix Date: Thu, 30 May 2024 14:04:54 +0200 Subject: [PATCH 096/189] release candidate --- .../splines_linear_problem_2x2_blocks.hpp | 112 +++++++++--------- .../splines/splines_linear_problem_maker.hpp | 25 ++-- tests/splines/matrix.cpp | 27 ++++- 3 files changed, 96 insertions(+), 68 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp index 77fc98d5c..af34db319 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp @@ -8,23 +8,23 @@ #include #include -#if __has_include() -#include -#else -#include -#endif - #include "splines_linear_problem.hpp" #include "splines_linear_problem_dense.hpp" namespace ddc::detail { /** - * @brief A 2x2-blocks linear problem dedicated to the computation of a spline approximation, with all blocks except top-left being stored in dense format. + * @brief A 2x2-blocks linear problem dedicated to the computation of a spline approximation (taking in account boundary conditions), + * with all blocks except top-left one being stored in dense format. + * + * A = | Q | gamma | + * | lambda | delta | * - * The storage format is dense row-major for top-left and bottom-right blocks, the one of SplinesLinearProblemDense (which is also dense row-major in practice) for bottom-right block and undefined for the top-left one (determined by the type of top_left_block). + * The storage format is dense row-major for top-left, top-right and bottom-left blocks, and determined by + * its type for the top-left block. * - * This class implements a Schur complement method to perform a block-LU factorization and solve, calling tl_block and br_block setup_solver() and solve() methods for internal operations. + * This class implements a Schur complement method to perform a block-LU factorization and solve, + * calling top-left block and bottom-right block setup_solver() and solve() methods for internal operations. * * @tparam ExecSpace The Kokkos::ExecutionSpace on which operations related to the matrix are supposed to be performed. */ @@ -36,10 +36,6 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem using SplinesLinearProblem::size; protected: - /* - * A = | Q | gamma | - * | lambda | delta | - */ std::shared_ptr> m_top_left_block; Kokkos::View m_top_right_block; Kokkos::View m_bottom_left_block; @@ -50,6 +46,7 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem * @brief SplinesLinearProblem2x2Blocks constructor. * * @param mat_size The size of one of the dimensions of the square matrix. + * @param q A pointer toward the top-left SplinesLinearProblem. */ explicit SplinesLinearProblem2x2Blocks( std::size_t const mat_size, @@ -73,29 +70,6 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem Kokkos::deep_copy(m_bottom_left_block, 0.); } -protected: - explicit SplinesLinearProblem2x2Blocks( - std::size_t const mat_size, - std::unique_ptr> q, - std::size_t const bottom_left_block_size1, - std::size_t const bottom_left_block_size2) - : SplinesLinearProblem(mat_size) - , m_top_left_block(std::move(q)) - , m_top_right_block( - "top_right_block", - m_top_left_block->size(), - mat_size - m_top_left_block->size()) - , m_bottom_left_block("bottom_left_block", bottom_left_block_size1, bottom_left_block_size2) - , m_bottom_right_block( - new SplinesLinearProblemDense(mat_size - m_top_left_block->size())) - { - assert(m_top_left_block->size() <= mat_size); - - Kokkos::deep_copy(m_top_right_block, 0.); - Kokkos::deep_copy(m_bottom_left_block, 0.); - } - -public: virtual double get_element(std::size_t const i, std::size_t const j) const override { assert(i < size()); @@ -131,6 +105,7 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem } private: + // @brief Compute the Schur complement delta - lambda*Q^-1*gamma. virtual void compute_schur_complement() { Kokkos::parallel_for( @@ -158,8 +133,9 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem * | lambda | delta - lambda*Q^-1*gamma | | 0 | I | * * So we perform the factorization inplace to store only the relevant blocks in the matrix (while factorizing - * the blocks themselves): - * | Q | Q^-1*gamma | + * the blocks themselves if necessary): + * + * | Q | Q^-1*gamma | * | lambda | delta - lambda*Q^-1*gamma | */ void setup_solver() override @@ -178,9 +154,14 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem } /** + * @brief Compute v <- v - lambda*u. + * * [SHOULD BE PRIVATE (GPU programming limitation)] + * + * @param u Upper part of the multiple right-hand sides + * @param v Lower part of the multiple right-hand sides */ - virtual void solve_bottom_left_block_section(MultiRHS const v, MultiRHS const u) const + virtual void solve_bottom_left_block_section(MultiRHS const u, MultiRHS v) const { auto bottom_left_block_device = create_mirror_view_and_copy(ExecSpace(), m_bottom_left_block); @@ -204,9 +185,14 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem } /** + * @brief Compute u <- u - lambda^t*v. + * * [SHOULD BE PRIVATE (GPU programming limitation)] + * + * @param u Upper part of the multiple right-hand sides + * @param v Lower part of the multiple right-hand sides */ - virtual void solve_bottom_left_block_section_transpose(MultiRHS const u, MultiRHS const v) const + virtual void solve_bottom_left_block_section_transpose(MultiRHS u, MultiRHS const v) const { auto bottom_left_block_device = create_mirror_view_and_copy(ExecSpace(), m_bottom_left_block); @@ -230,9 +216,14 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem } /** + * @brief Compute u <- u - gamma*v. + * * [SHOULD BE PRIVATE (GPU programming limitation)] + * + * @param u Upper part of the multiple right-hand sides + * @param v Lower part of the multiple right-hand sides */ - virtual void solve_top_right_block_section(MultiRHS const u, MultiRHS const v) const + virtual void solve_top_right_block_section(MultiRHS u, MultiRHS const v) const { auto top_right_block_device = create_mirror_view_and_copy(ExecSpace(), m_top_right_block); Kokkos::parallel_for( @@ -255,9 +246,14 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem } /** + * @brief Compute v <- v - gamma^t*u. + * * [SHOULD BE PRIVATE (GPU programming limitation)] + * + * @param u Upper part of the multiple right-hand sides + * @param v Lower part of the multiple right-hand sides */ - virtual void solve_top_right_block_section_transpose(MultiRHS const v, MultiRHS const u) const + virtual void solve_top_right_block_section_transpose(MultiRHS const u, MultiRHS v) const { auto top_right_block_device = create_mirror_view_and_copy(ExecSpace(), m_top_right_block); Kokkos::parallel_for( @@ -282,7 +278,17 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem /** * @brief Solve the multiple right-hand sides linear problem Ax=b or its transposed version A^tx=b inplace. * - * The solver method is band gaussian elimination with partial pivoting using the LU-factorized matrix A. The implementation is LAPACK method dgbtrs. + * The solver method is the one known as Schur complement method. It can be summarized as follow, + * starting with the pre-computed elements of the matrix: + * + * | Q | Q^-1*gamma | + * | lambda | delta - lambda*Q^-1*gamma | + * + * For the non-transposed case: + * - Solve inplace Q * x'1 = b1 (using the solver internal to Q). + * - Compute inplace b'2 = b2 - lambda*x'1. + * - Solve inplace (delta - lambda*Q^-1*gamma) * x2 = b'2. + * - Compute inplace x1 = x'1 - (delta - lambda*Q^-1*gamma)*x2. * * @param[in, out] b A 2D Kokkos::View storing the multiple right-hand sides of the problem and receiving the corresponding solution. * @param transpose Choose between the direct or transposed version of the linear problem. @@ -291,24 +297,24 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem { assert(b.extent(0) == size()); - MultiRHS u = Kokkos:: + MultiRHS b1 = Kokkos:: subview(b, std::pair(0, m_top_left_block->size()), Kokkos::ALL); - MultiRHS v = Kokkos:: + MultiRHS b2 = Kokkos:: subview(b, std::pair(m_top_left_block->size(), b.extent(0)), Kokkos::ALL); if (!transpose) { - m_top_left_block->solve(u); - solve_bottom_left_block_section(v, u); - m_bottom_right_block->solve(v); - solve_top_right_block_section(u, v); + m_top_left_block->solve(b1); + solve_bottom_left_block_section(b1, b2); + m_bottom_right_block->solve(b2); + solve_top_right_block_section(b1, b2); } else { - solve_top_right_block_section_transpose(v, u); - m_bottom_right_block->solve(v, true); - solve_bottom_left_block_section_transpose(u, v); - m_top_left_block->solve(u, true); + solve_top_right_block_section_transpose(b1, b2); + m_bottom_right_block->solve(b2, true); + solve_bottom_left_block_section_transpose(b1, b2); + m_top_left_block->solve(b1, true); } } }; diff --git a/include/ddc/kernels/splines/splines_linear_problem_maker.hpp b/include/ddc/kernels/splines/splines_linear_problem_maker.hpp index fc2af59b7..0c676a42c 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_maker.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_maker.hpp @@ -62,31 +62,28 @@ class SplinesLinearProblemMaker } /** - * @brief Construct a 2x2-blocks with band top-left block matrix + * @brief Construct a 2x2-blocks linear problem with band "main" block (the one called + * Q in SplinesLinearProblem2x2Blocks). * * @tparam the Kokkos::ExecutionSpace on which matrix-related operation will be performed. - * @param n The size of one of the dimensions of the square matrix. - * @param kl The number of subdiagonals. - * @param ku The number of superdiagonals. - * @param pds A boolean indicating if the matrix is positive-definite symetric or not. + * @param n The size of one of the dimensions of the whole square matrix. + * @param kl The number of subdiagonals in the band block. + * @param ku The number of superdiagonals in the band block. + * @param pds A boolean indicating if the band block is positive-definite symetric or not. + * @param bottom_right_size The size of one of the dimensions of the bottom-right block. * * @return The SplinesLinearProblem instance. */ template - static std::unique_ptr> make_new_2x2_blocks_with_band_top_left( + static std::unique_ptr> + make_new_block_matrix_with_band_main_block( int const n, int const kl, int const ku, bool const pds, - int const block1_size, - int const block2_size = 0) + int const bottom_right_size) { - assert(block2_size - == 0); // block2_size is a placeholder while SplinesLinearProblem3x3Blocks is not implemented. - - // TODO: clarify if top-left or bottom_right is the band - - int const top_left_size = n - block1_size - block2_size; + int const top_left_size = n - bottom_right_size; std::unique_ptr> top_left_block = make_new_band(top_left_size, kl, ku, pds); return std::make_unique< diff --git a/tests/splines/matrix.cpp b/tests/splines/matrix.cpp index aa911f332..71bef60a5 100644 --- a/tests/splines/matrix.cpp +++ b/tests/splines/matrix.cpp @@ -201,6 +201,31 @@ TEST(Matrix, PDSBand) solve_and_validate(*matrix); } +TEST(Matrix, 2x2Blocks) +{ + std::size_t const N = 10; + std::size_t const k = 10; + std::unique_ptr> top_left_block + = std::make_unique< + ddc::detail::SplinesLinearProblemDense>(3); + std::unique_ptr> matrix + = std::make_unique>(N, std::move(top_left_block)); + + // Build a non-symmetric full-rank matrix (without zero) + for (std::size_t i(0); i < N; ++i) { + matrix->set_element(i, i, 3. / 4 * ((N + 1) * i + 1)); + for (std::size_t j(std::max(0, int(i) - int(k))); j < i; ++j) { + matrix->set_element(i, j, -(1. / 4) / k * (N * i + j + 1)); + } + for (std::size_t j(i + 1); j < std::min(N, i + k + 1); ++j) { + matrix->set_element(i, j, -(1. / 4) / k * (N * i + j + 1)); + } + } + + solve_and_validate(*matrix); +} + class MatrixSizesFixture : public testing::TestWithParam> { }; @@ -274,7 +299,7 @@ TEST_P(MatrixSizesFixture, 2x2Blocks) { auto const [N, k] = GetParam(); std::unique_ptr> matrix - = ddc::detail::SplinesLinearProblemMaker::make_new_2x2_blocks_with_band_top_left< + = ddc::detail::SplinesLinearProblemMaker::make_new_block_matrix_with_band_main_block< Kokkos::DefaultExecutionSpace>(N, k, k, false, 3); // Build a non-symmetric full-rank band matrix From 4cc3a1d65488725d19d6505487789496b68ecedf Mon Sep 17 00:00:00 2001 From: blegouix Date: Thu, 30 May 2024 14:18:35 +0200 Subject: [PATCH 097/189] autoreview --- .../splines_linear_problem_2x2_blocks.hpp | 20 ++++++++----------- 1 file changed, 8 insertions(+), 12 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp index af34db319..701b93487 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp @@ -158,8 +158,8 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem * * [SHOULD BE PRIVATE (GPU programming limitation)] * - * @param u Upper part of the multiple right-hand sides - * @param v Lower part of the multiple right-hand sides + * @param u + * @param v */ virtual void solve_bottom_left_block_section(MultiRHS const u, MultiRHS v) const { @@ -176,7 +176,6 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem Kokkos::parallel_for( Kokkos::TeamThreadRange(teamMember, v.extent(0)), [&](const int i) { - // Upper diagonals in bottom_left_block for (int l = 0; l < u.extent(0); ++l) { v(i, j) -= bottom_left_block_device(i, l) * u(l, j); } @@ -189,8 +188,8 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem * * [SHOULD BE PRIVATE (GPU programming limitation)] * - * @param u Upper part of the multiple right-hand sides - * @param v Lower part of the multiple right-hand sides + * @param u + * @param v */ virtual void solve_bottom_left_block_section_transpose(MultiRHS u, MultiRHS const v) const { @@ -207,7 +206,6 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem Kokkos::parallel_for( Kokkos::TeamThreadRange(teamMember, u.extent(0)), [&](const int i) { - // Upper diagonals in bottom_left_block for (int l = 0; l < v.extent(0); ++l) { u(i, j) -= bottom_left_block_device(l, i) * v(l, j); } @@ -220,8 +218,8 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem * * [SHOULD BE PRIVATE (GPU programming limitation)] * - * @param u Upper part of the multiple right-hand sides - * @param v Lower part of the multiple right-hand sides + * @param u + * @param v */ virtual void solve_top_right_block_section(MultiRHS u, MultiRHS const v) const { @@ -237,7 +235,6 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem Kokkos::parallel_for( Kokkos::TeamThreadRange(teamMember, u.extent(0)), [&](const int i) { - // Upper diagonals in bottom_left_block for (int l = 0; l < v.extent(0); ++l) { u(i, j) -= top_right_block_device(i, l) * v(l, j); } @@ -250,8 +247,8 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem * * [SHOULD BE PRIVATE (GPU programming limitation)] * - * @param u Upper part of the multiple right-hand sides - * @param v Lower part of the multiple right-hand sides + * @param u + * @param v */ virtual void solve_top_right_block_section_transpose(MultiRHS const u, MultiRHS v) const { @@ -267,7 +264,6 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem Kokkos::parallel_for( Kokkos::TeamThreadRange(teamMember, v.extent(0)), [&](const int i) { - // Upper diagonals in bottom_left_block for (int l = 0; l < u.extent(0); ++l) { v(i, j) -= top_right_block_device(l, i) * u(l, j); } From ed6115b17ff46f9629975ff08978c4aae462687e Mon Sep 17 00:00:00 2001 From: blegouix Date: Thu, 30 May 2024 14:25:43 +0200 Subject: [PATCH 098/189] autoreview --- .../ddc/kernels/splines/splines_linear_problem_maker.hpp | 6 +++--- tests/splines/matrix.cpp | 2 ++ 2 files changed, 5 insertions(+), 3 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_maker.hpp b/include/ddc/kernels/splines/splines_linear_problem_maker.hpp index bdb0f1112..3823ac89c 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_maker.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_maker.hpp @@ -84,11 +84,11 @@ class SplinesLinearProblemMaker int const kl, int const ku, bool const pds, - int const bottom_right_size) + int const bottom_size) { - int const top_left_size = n - bottom_right_size; + int const top_size = n - bottom_size; std::unique_ptr> top_left_block - = make_new_band(top_left_size, kl, ku, pds); + = make_new_band(top_size, kl, ku, pds); return std::make_unique< SplinesLinearProblem2x2Blocks>(n, std::move(top_left_block)); } diff --git a/tests/splines/matrix.cpp b/tests/splines/matrix.cpp index 2c87e6036..7498da566 100644 --- a/tests/splines/matrix.cpp +++ b/tests/splines/matrix.cpp @@ -219,6 +219,8 @@ TEST(Matrix, PDSTridiag) matrix->set_element(i, j, -1.0); } } + + solve_and_validate(*matrix); } TEST(Matrix, 2x2Blocks) From 21155ff4f9c1acaf668a5ba54ea55e24f0d1ae4f Mon Sep 17 00:00:00 2001 From: blegouix Date: Fri, 31 May 2024 11:22:51 +0200 Subject: [PATCH 099/189] wip --- .../splines_linear_problem_2x2_blocks.hpp | 70 ++++++++++++------- 1 file changed, 44 insertions(+), 26 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp index 701b93487..5290a0459 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp @@ -8,6 +8,8 @@ #include #include +#include + #include "splines_linear_problem.hpp" #include "splines_linear_problem_dense.hpp" @@ -36,10 +38,12 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem using SplinesLinearProblem::size; protected: - std::shared_ptr> m_top_left_block; - Kokkos::View m_top_right_block; - Kokkos::View m_bottom_left_block; - std::shared_ptr> m_bottom_right_block; + std::unique_ptr> m_top_left_block; + Kokkos::DualView + m_top_right_block; + Kokkos::DualView + m_bottom_left_block; + std::unique_ptr> m_bottom_right_block; public: /** @@ -66,8 +70,8 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem { assert(m_top_left_block->size() <= mat_size); - Kokkos::deep_copy(m_top_right_block, 0.); - Kokkos::deep_copy(m_bottom_left_block, 0.); + Kokkos::deep_copy(m_top_right_block.h_view, 0.); + Kokkos::deep_copy(m_bottom_left_block.h_view, 0.); } virtual double get_element(std::size_t const i, std::size_t const j) const override @@ -81,9 +85,9 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem } else if (i >= nq && j >= nq) { return m_bottom_right_block->get_element(i - nq, j - nq); } else if (j >= nq) { - return m_top_right_block(i, j - nq); + return m_top_right_block.h_view(i, j - nq); } else { - return m_bottom_left_block(i - nq, j); + return m_bottom_left_block.h_view(i - nq, j); } } @@ -98,9 +102,9 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem } else if (i >= nq && j >= nq) { m_bottom_right_block->set_element(i - nq, j - nq, aij); } else if (j >= nq) { - m_top_right_block(i, j - nq) = aij; + m_top_right_block.h_view(i, j - nq) = aij; } else { - m_bottom_left_block(i - nq, j) = aij; + m_bottom_left_block.h_view(i - nq, j) = aij; } } @@ -116,7 +120,7 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem [&](const int i, const int j) { double val = 0.0; for (int l = 0; l < m_top_left_block->size(); ++l) { - val += m_bottom_left_block(i, l) * m_top_right_block(l, j); + val += m_bottom_left_block.h_view(i, l) * m_top_right_block.h_view(l, j); } m_bottom_right_block ->set_element(i, j, m_bottom_right_block->get_element(i, j) - val); @@ -140,16 +144,24 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem */ void setup_solver() override { + // Setup the top-left solver m_top_left_block->setup_solver(); - // Compute Q^-1*gamma - auto top_right_block_device = create_mirror_view_and_copy(ExecSpace(), m_top_right_block); - m_top_left_block->solve(top_right_block_device); - deep_copy(m_top_right_block, top_right_block_device); + // Compute Q^-1*gamma in top-right block + m_top_right_block.modify_host(); + m_top_right_block.sync_device(); + m_top_left_block->solve(m_top_right_block.d_view); + m_top_right_block.modify_device(); + m_top_right_block.sync_host(); + + // Push lambda on device in bottom-left block + m_bottom_left_block.modify_host(); + m_bottom_left_block.sync_device(); - // Compute delta - lambda*Q^-1*gamma + // Compute delta - lambda*Q^-1*gamma in bottom-right block compute_schur_complement(); + // Setup the bottom-right solver m_bottom_right_block->setup_solver(); } @@ -161,10 +173,11 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem * @param u * @param v */ - virtual void solve_bottom_left_block_section(MultiRHS const u, MultiRHS v) const + virtual void solve_bottom_left_block_section(MultiRHS const u, MultiRHS const v) const { - auto bottom_left_block_device - = create_mirror_view_and_copy(ExecSpace(), m_bottom_left_block); + Kokkos::View + bottom_left_block_device = m_bottom_left_block.d_view; + Kokkos::parallel_for( "solve_bottom_left_block_section", Kokkos::TeamPolicy(v.extent(1), Kokkos::AUTO), @@ -191,10 +204,11 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem * @param u * @param v */ - virtual void solve_bottom_left_block_section_transpose(MultiRHS u, MultiRHS const v) const + virtual void solve_bottom_left_block_section_transpose(MultiRHS const u, MultiRHS const v) const { - auto bottom_left_block_device - = create_mirror_view_and_copy(ExecSpace(), m_bottom_left_block); + Kokkos::View + bottom_left_block_device = m_bottom_left_block.d_view; + Kokkos::parallel_for( "solve_bottom_left_block_section_transpose", Kokkos::TeamPolicy(u.extent(1), Kokkos::AUTO), @@ -221,9 +235,11 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem * @param u * @param v */ - virtual void solve_top_right_block_section(MultiRHS u, MultiRHS const v) const + virtual void solve_top_right_block_section(MultiRHS const u, MultiRHS const v) const { - auto top_right_block_device = create_mirror_view_and_copy(ExecSpace(), m_top_right_block); + Kokkos::View + top_right_block_device = m_top_right_block.d_view; + Kokkos::parallel_for( "solve_top_right_block_section", Kokkos::TeamPolicy(u.extent(1), Kokkos::AUTO), @@ -250,9 +266,11 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem * @param u * @param v */ - virtual void solve_top_right_block_section_transpose(MultiRHS const u, MultiRHS v) const + virtual void solve_top_right_block_section_transpose(MultiRHS const u, MultiRHS const v) const { - auto top_right_block_device = create_mirror_view_and_copy(ExecSpace(), m_top_right_block); + Kokkos::View + top_right_block_device = m_top_right_block.d_view; + Kokkos::parallel_for( "solve_top_right_block_section_transpose", Kokkos::TeamPolicy(v.extent(1), Kokkos::AUTO), From 3793667f3f234d030a37ee22bce7e4b71685e87b Mon Sep 17 00:00:00 2001 From: blegouix Date: Fri, 31 May 2024 12:13:32 +0200 Subject: [PATCH 100/189] wip --- .../splines_linear_problem_2x2_blocks.hpp | 136 ++++-------------- 1 file changed, 25 insertions(+), 111 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp index 5290a0459..0f8f1f9b8 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp @@ -166,124 +166,38 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem } /** - * @brief Compute v <- v - lambda*u. + * @brief Compute y <- y - LinOp*x or y <- y - LinOp^t*x. * * [SHOULD BE PRIVATE (GPU programming limitation)] * - * @param u - * @param v + * @param x + * @param y + * @param LinOp + * @param transpose */ - virtual void solve_bottom_left_block_section(MultiRHS const u, MultiRHS const v) const + void gemv_minus1_1( + MultiRHS const x, + MultiRHS const y, + Kokkos::View const + LinOp, + bool const transpose = false) const { - Kokkos::View - bottom_left_block_device = m_bottom_left_block.d_view; - - Kokkos::parallel_for( - "solve_bottom_left_block_section", - Kokkos::TeamPolicy(v.extent(1), Kokkos::AUTO), - KOKKOS_LAMBDA( - const typename Kokkos::TeamPolicy::member_type& teamMember) { - const int j = teamMember.league_rank(); - - - Kokkos::parallel_for( - Kokkos::TeamThreadRange(teamMember, v.extent(0)), - [&](const int i) { - for (int l = 0; l < u.extent(0); ++l) { - v(i, j) -= bottom_left_block_device(i, l) * u(l, j); - } - }); - }); - } - - /** - * @brief Compute u <- u - lambda^t*v. - * - * [SHOULD BE PRIVATE (GPU programming limitation)] - * - * @param u - * @param v - */ - virtual void solve_bottom_left_block_section_transpose(MultiRHS const u, MultiRHS const v) const - { - Kokkos::View - bottom_left_block_device = m_bottom_left_block.d_view; - Kokkos::parallel_for( - "solve_bottom_left_block_section_transpose", - Kokkos::TeamPolicy(u.extent(1), Kokkos::AUTO), + "gemv_minus1_1", + Kokkos::TeamPolicy(y.extent(1), Kokkos::AUTO), KOKKOS_LAMBDA( const typename Kokkos::TeamPolicy::member_type& teamMember) { const int j = teamMember.league_rank(); - - Kokkos::parallel_for( - Kokkos::TeamThreadRange(teamMember, u.extent(0)), - [&](const int i) { - for (int l = 0; l < v.extent(0); ++l) { - u(i, j) -= bottom_left_block_device(l, i) * v(l, j); - } - }); - }); - } - - /** - * @brief Compute u <- u - gamma*v. - * - * [SHOULD BE PRIVATE (GPU programming limitation)] - * - * @param u - * @param v - */ - virtual void solve_top_right_block_section(MultiRHS const u, MultiRHS const v) const - { - Kokkos::View - top_right_block_device = m_top_right_block.d_view; - - Kokkos::parallel_for( - "solve_top_right_block_section", - Kokkos::TeamPolicy(u.extent(1), Kokkos::AUTO), - KOKKOS_LAMBDA( - const typename Kokkos::TeamPolicy::member_type& teamMember) { - const int j = teamMember.league_rank(); - - - Kokkos::parallel_for( - Kokkos::TeamThreadRange(teamMember, u.extent(0)), - [&](const int i) { - for (int l = 0; l < v.extent(0); ++l) { - u(i, j) -= top_right_block_device(i, l) * v(l, j); - } - }); - }); - } - - /** - * @brief Compute v <- v - gamma^t*u. - * - * [SHOULD BE PRIVATE (GPU programming limitation)] - * - * @param u - * @param v - */ - virtual void solve_top_right_block_section_transpose(MultiRHS const u, MultiRHS const v) const - { - Kokkos::View - top_right_block_device = m_top_right_block.d_view; - - Kokkos::parallel_for( - "solve_top_right_block_section_transpose", - Kokkos::TeamPolicy(v.extent(1), Kokkos::AUTO), - KOKKOS_LAMBDA( - const typename Kokkos::TeamPolicy::member_type& teamMember) { - const int j = teamMember.league_rank(); - - Kokkos::parallel_for( - Kokkos::TeamThreadRange(teamMember, v.extent(0)), - [&](const int i) { - for (int l = 0; l < u.extent(0); ++l) { - v(i, j) -= top_right_block_device(l, i) * u(l, j); + Kokkos::TeamThreadRange(teamMember, y.extent(0)), + [&](int const i) { + for (int l = 0; l < x.extent(0); ++l) { + if (!transpose) { + y(i, j) -= LinOp(i, l) * x(l, j); + } else { + y(i, j) -= LinOp(l, i) * x(l, j); + } } }); }); @@ -321,13 +235,13 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem Kokkos::ALL); if (!transpose) { m_top_left_block->solve(b1); - solve_bottom_left_block_section(b1, b2); + gemv_minus1_1(b1, b2, m_bottom_left_block.d_view); m_bottom_right_block->solve(b2); - solve_top_right_block_section(b1, b2); + gemv_minus1_1(b2, b1, m_top_right_block.d_view); } else { - solve_top_right_block_section_transpose(b1, b2); + gemv_minus1_1(b1, b2, m_top_right_block.d_view, true); m_bottom_right_block->solve(b2, true); - solve_bottom_left_block_section_transpose(b1, b2); + gemv_minus1_1(b2, b1, m_bottom_left_block.d_view, true); m_top_left_block->solve(b1, true); } } From a158101e49ac2eaff74aa002aeb0b1b72ee87fe1 Mon Sep 17 00:00:00 2001 From: blegouix Date: Fri, 31 May 2024 12:27:00 +0200 Subject: [PATCH 101/189] thomas' review --- .../kernels/splines/splines_linear_problem_2x2_blocks.hpp | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp index 0f8f1f9b8..282d54b5b 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp @@ -74,7 +74,7 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem Kokkos::deep_copy(m_bottom_left_block.h_view, 0.); } - virtual double get_element(std::size_t const i, std::size_t const j) const override + double get_element(std::size_t const i, std::size_t const j) const override { assert(i < size()); assert(j < size()); @@ -91,7 +91,7 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem } } - virtual void set_element(std::size_t const i, std::size_t const j, double const aij) override + void set_element(std::size_t const i, std::size_t const j, double const aij) override { assert(i < size()); assert(j < size()); @@ -110,7 +110,7 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem private: // @brief Compute the Schur complement delta - lambda*Q^-1*gamma. - virtual void compute_schur_complement() + void compute_schur_complement() { Kokkos::parallel_for( "compute_schur_complement", From 7fec07c54139cfb5298ec92b7a1d59e665a0dd52 Mon Sep 17 00:00:00 2001 From: blegouix Date: Fri, 31 May 2024 20:50:49 +0200 Subject: [PATCH 102/189] improve gemv --- .../splines_linear_problem_2x2_blocks.hpp | 36 ++++++++++++------- 1 file changed, 23 insertions(+), 13 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp index 282d54b5b..8d0147d88 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp @@ -182,24 +182,34 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem LinOp, bool const transpose = false) const { + assert(!transpose && LinOp.extent(0) == y.extent(0) + || transpose && LinOp.extent(1) == y.extent(0)); + assert(!transpose && LinOp.extent(1) == x.extent(0) + || transpose && LinOp.extent(0) == x.extent(0)); + assert(x.extent(1) == y.extent(1)); + Kokkos::parallel_for( "gemv_minus1_1", - Kokkos::TeamPolicy(y.extent(1), Kokkos::AUTO), + Kokkos::TeamPolicy(y.extent(0) * y.extent(1), Kokkos::AUTO), KOKKOS_LAMBDA( const typename Kokkos::TeamPolicy::member_type& teamMember) { - const int j = teamMember.league_rank(); - - Kokkos::parallel_for( - Kokkos::TeamThreadRange(teamMember, y.extent(0)), - [&](int const i) { - for (int l = 0; l < x.extent(0); ++l) { - if (!transpose) { - y(i, j) -= LinOp(i, l) * x(l, j); - } else { - y(i, j) -= LinOp(l, i) * x(l, j); - } + const int i = teamMember.league_rank() / y.extent(1); + const int j = teamMember.league_rank() % y.extent(1); + + double LinOpTimesX = 0.; + Kokkos::parallel_reduce( + Kokkos::TeamThreadRange(teamMember, x.extent(0)), + [&](const int l, double& y_tmp) { + if (!transpose) { + y_tmp += LinOp(i, l) * x(l, j); + } else { + y_tmp += LinOp(l, i) * x(l, j); } - }); + }, + LinOpTimesX); + if (teamMember.team_rank() == 0) { + y(i, j) -= LinOpTimesX; + } }); } From 4f0422a2fad0f38101956949741ca4db57144601 Mon Sep 17 00:00:00 2001 From: blegouix Date: Fri, 31 May 2024 20:58:43 +0200 Subject: [PATCH 103/189] minor fix --- .../ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp index 8d0147d88..a101c7181 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp @@ -66,7 +66,7 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem mat_size - m_top_left_block->size(), m_top_left_block->size()) , m_bottom_right_block( - new SplinesLinearProblemDense(mat_size - m_top_left_block->size())) + new SplinesLinearProblemDense(mat_size - top_left_block->size())) { assert(m_top_left_block->size() <= mat_size); From 3b6d736c34493774e2524b7bb39cf01c9b6369b0 Mon Sep 17 00:00:00 2001 From: blegouix Date: Fri, 31 May 2024 20:59:30 +0200 Subject: [PATCH 104/189] minor fix --- .../ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp index a101c7181..07754efd1 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp @@ -54,9 +54,9 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem */ explicit SplinesLinearProblem2x2Blocks( std::size_t const mat_size, - std::unique_ptr> q) + std::unique_ptr> top_left_block) : SplinesLinearProblem(mat_size) - , m_top_left_block(std::move(q)) + , m_top_left_block(std::move(top_left_block)) , m_top_right_block( "top_right_block", m_top_left_block->size(), From a49541d5771d2abaf35c8bd0cb01e11e5f8d563f Mon Sep 17 00:00:00 2001 From: blegouix Date: Fri, 31 May 2024 21:01:41 +0200 Subject: [PATCH 105/189] renaming --- .../kernels/splines/splines_linear_problem_2x2_blocks.hpp | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp index 07754efd1..d7cf29ad4 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp @@ -199,11 +199,11 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem double LinOpTimesX = 0.; Kokkos::parallel_reduce( Kokkos::TeamThreadRange(teamMember, x.extent(0)), - [&](const int l, double& y_tmp) { + [&](const int l, double& LinOpTimesX_tmp) { if (!transpose) { - y_tmp += LinOp(i, l) * x(l, j); + LinOpTimesX_tmp += LinOp(i, l) * x(l, j); } else { - y_tmp += LinOp(l, i) * x(l, j); + LinOpTimesX_tmp += LinOp(l, i) * x(l, j); } }, LinOpTimesX); From d0bb2de75cf56c35b21181922813fad95aa442c4 Mon Sep 17 00:00:00 2001 From: blegouix Date: Sat, 1 Jun 2024 10:22:47 +0200 Subject: [PATCH 106/189] fix --- .../ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp index d7cf29ad4..e46c79825 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp @@ -66,7 +66,7 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem mat_size - m_top_left_block->size(), m_top_left_block->size()) , m_bottom_right_block( - new SplinesLinearProblemDense(mat_size - top_left_block->size())) + new SplinesLinearProblemDense(mat_size - m_top_left_block->size())) { assert(m_top_left_block->size() <= mat_size); From 5da58468039450b8cc871cc980970cc88f62749e Mon Sep 17 00:00:00 2001 From: Baptiste Legouix Date: Sat, 1 Jun 2024 10:28:20 +0200 Subject: [PATCH 107/189] Update include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp --- .../ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp index e46c79825..89de9ba61 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp @@ -158,10 +158,8 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem m_bottom_left_block.modify_host(); m_bottom_left_block.sync_device(); - // Compute delta - lambda*Q^-1*gamma in bottom-right block + // Compute delta - lambda*Q^-1*gamma in bottom-right block & setup the bottom-right solver compute_schur_complement(); - - // Setup the bottom-right solver m_bottom_right_block->setup_solver(); } From 242ec03fa4b0896a33140b4e32cdb2f5c5ba1580 Mon Sep 17 00:00:00 2001 From: blegouix Date: Sat, 1 Jun 2024 21:08:35 +0200 Subject: [PATCH 108/189] wip --- .../splines_linear_problem_periodic_band.hpp | 208 ++++++++++++++++++ 1 file changed, 208 insertions(+) create mode 100644 include/ddc/kernels/splines/splines_linear_problem_periodic_band.hpp diff --git a/include/ddc/kernels/splines/splines_linear_problem_periodic_band.hpp b/include/ddc/kernels/splines/splines_linear_problem_periodic_band.hpp new file mode 100644 index 000000000..f1da6beac --- /dev/null +++ b/include/ddc/kernels/splines/splines_linear_problem_periodic_band.hpp @@ -0,0 +1,208 @@ +// Copyright (C) The DDC development team, see COPYRIGHT.md file +// +// SPDX-License-Identifier: MIT + +#pragma once + +#include +#include +#include + +#include + +#include "splines_linear_problem.hpp" +#include "splines_linear_problem_dense.hpp" + +namespace ddc::detail { + +/** + * @brief A periodic-band linear problem dedicated to the computation of a spline approximation (taking in account boundary conditions), + * with all blocks except top-left one being stored in dense format. + * + * A = | Q | gamma | + * | lambda | delta | + * + * The storage format is dense row-major for top-left, top-right and bottom-left blocks, and determined by + * its type for the top-left block. + * + * This class implements a Schur complement method to perform a block-LU factorization and solve, + * calling top-left block and bottom-right block setup_solver() and solve() methods for internal operations. + * + * @tparam ExecSpace The Kokkos::ExecutionSpace on which operations related to the matrix are supposed to be performed. + */ +template +class SplinesLinearProblemPeriodicBand : public SplinesLinearProblem2x2Blocks +{ +public: + using typename SplinesLinearProblem2x2Blocks::MultiRHS; + using SplinesLinearProblem2x2Blocks::size; + +protected: + std::size_t m_kl; // no. of subdiagonals + std::size_t m_ku; // no. of superdiagonals + +public: + /** + * @brief SplinesLinearProblem2x2Blocks constructor. + * + * @param mat_size The size of one of the dimensions of the square matrix. + * @param q A pointer toward the top-left SplinesLinearProblem. + */ + explicit SplinesLinearProblemPeriodicBand( + std::size_t const mat_size, + std::size_t const kl, + std::size_t const ku, + std::unique_ptr> top_left_block) + : SplinesLinearProblem2x2Blocks(mat_size, std::move(top_left_block)) + { + } + + double get_element(std::size_t const i, std::size_t const j) const override + { + assert(i < size()); + assert(j < size()); + + std::size_t const nq = m_top_left_block->size(); + std::size_t const ndelta = m_bottom_right_block->size(); + if (i >= nq && j < nq) { + std::size_t const d = j - i; + if (d > size() / 2) + d -= size(); + if (d < -size() / 2) + d += size(); + + if (d < -m_kl || d > m_ku) + return 0.0; + if (d > 0) { + return m_bottom_left_block(i - nq, j); + } else { + return m_bottom_left_block(i - nq, j - nq + ndelta + 1); + } + } else { + return MatrixCornerBlock::get_element(i, j); + } + } + + void set_element(std::size_t const i, std::size_t const j, double const aij) override + { + assert(i < size()); + assert(j < size()); + + std::size_t const nq = m_top_left_block->size(); + std::size_t const ndelta = m_bottom_right_block->size(); + if (i >= nq && j < nq) { + int d = j - i; + if (d > size() / 2) + d -= size(); + if (d < -size() / 2) + d += size(); + + if (d < -m_kl || d > m_ku) { + assert(std::fabs(aij) < 1e-20); + return; + } + + if (d > 0) { + m_bottom_left_block(i - nq, j) = aij; + } else { + m_bottom_left_block(i - nq, j - nq + ndelta + 1) = aij; + } + } else { + MatrixCornerBlock::set_element(i, j, aij); + } + } + +private: + // @brief Compute the Schur complement delta - lambda*Q^-1*gamma. + void compute_schur_complement() + { + Kokkos::parallel_for( + "compute_schur_complement", + Kokkos::MDRangePolicy>( + {0, 0}, + {m_bottom_right_block->size(), m_bottom_right_block->size()}), + [&](const int i, const int j) { + double val = 0.0; + // Upper diagonals in lambda, lower diagonals in gamma + for (int l = 0; l < i + 1; ++l) { + val += m_bottom_left_block.h_view(i, l) * m_top_right_block.h_view(l, j); + } + // Lower diagonals in lambda, upper diagonals in gamma + for (int l = i + 1; l < m_bottom_right_block->size() + 1; ++l) { + int const l_full + = m_top_left_block->size() - 1 - m_bottom_right_block->size() + l; + val += m_bottom_left_block.h_view(i, l) + * m_top_right_block.h_view(l_full, j); + } + m_bottom_right_block + ->set_element(i, j, m_bottom_right_block->get_element(i, j) - val); + }); + } + + /** + * @brief Compute y <- y - LinOp*x or y <- y - LinOp^t*x. + * + * [SHOULD BE PRIVATE (GPU programming limitation)] + * + * @param x + * @param y + * @param LinOp + * @param transpose + */ + void gemv_minus1_1( + MultiRHS const x, + MultiRHS const y, + Kokkos::View const + LinOp, + bool const transpose = false) const + { + assert(!transpose && LinOp.extent(0) == y.extent(0) + || transpose && LinOp.extent(1) == y.extent(0)); + assert(!transpose && LinOp.extent(1) == x.extent(0) + || transpose && LinOp.extent(0) == x.extent(0)); + assert(x.extent(1) == y.extent(1)); + + Kokkos::parallel_for( + "gemv_minus1_1", + Kokkos::TeamPolicy(y.extent(0) * y.extent(1), Kokkos::AUTO), + KOKKOS_LAMBDA( + const typename Kokkos::TeamPolicy::member_type& teamMember) { + const int i = teamMember.league_rank() / y.extent(1); + const int j = teamMember.league_rank() % y.extent(1); + + double LinOpTimesX = 0.; + Kokkos::parallel_reduce( + Kokkos::TeamThreadRange(teamMember, !transpose ? i + 1 : i), + [&](const int l, double& LinOpTimesX_tmp) { + if (!transpose) { + LinOpTimesX_tmp += LinOp(i, l) * x(l, j); + } else { + LinOpTimesX_tmp += LinOp(l, i) * x(l, j); + } + }, + LinOpTimesX); + teamMember.team_barrier(); + double LinOpTimesX2 = 0.; + Kokkos::parallel_reduce( + Kokkos::TeamThreadRange( + teamMember, + !transpose ? i + 1 : i, + x.extent(0)), + [&](const int l, double& LinOpTimesX_tmp) { + int const l_full = m_top_left_block->size() - 1 + - m_bottom_right_block->size() + l; + if (!transpose) { + LinOpTimesX_tmp += LinOp(i, l) * x(l_full, j); + } else { + LinOpTimesX_tmp += LinOp(l, i) * x(l_full, j); + } + }, + LinOpTimesX2); + if (teamMember.team_rank() == 0) { + y(i, j) -= LinOpTimesX + LinOpTimesX2; + } + }); + } +}; + +} // namespace ddc::detail From 435efcd8c3591b3b79184b660b52527f11ea8423 Mon Sep 17 00:00:00 2001 From: blegouix Date: Mon, 3 Jun 2024 12:34:53 +0200 Subject: [PATCH 109/189] runs but wrong result --- include/ddc/kernels/splines.hpp | 1 + .../splines_linear_problem_2x2_blocks.hpp | 30 ++++++- .../splines/splines_linear_problem_maker.hpp | 39 +++++++++ .../splines_linear_problem_periodic_band.hpp | 86 ++++++++++++++++--- tests/splines/matrix.cpp | 54 ++++++++++++ 5 files changed, 195 insertions(+), 15 deletions(-) diff --git a/include/ddc/kernels/splines.hpp b/include/ddc/kernels/splines.hpp index 1cae877fd..c68c17266 100644 --- a/include/ddc/kernels/splines.hpp +++ b/include/ddc/kernels/splines.hpp @@ -25,5 +25,6 @@ #include "splines/splines_linear_problem_maker.hpp" #include "splines/splines_linear_problem_pds_band.hpp" #include "splines/splines_linear_problem_pds_tridiag.hpp" +#include "splines/splines_linear_problem_periodic_band.hpp" #include "splines/splines_linear_problem_sparse.hpp" #include "splines/view.hpp" diff --git a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp index e46c79825..f2819494b 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp @@ -74,6 +74,34 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem Kokkos::deep_copy(m_bottom_left_block.h_view, 0.); } +protected: + /** + * @brief SplinesLinearProblem2x2Blocks constructor. + * + * @param mat_size The size of one of the dimensions of the square matrix. + * @param q A pointer toward the top-left SplinesLinearProblem. + */ + explicit SplinesLinearProblem2x2Blocks( + std::size_t const mat_size, + std::unique_ptr> top_left_block, + std::size_t const lambda_size1, + std::size_t const lambda_size2) + : SplinesLinearProblem(mat_size) + , m_top_left_block(std::move(top_left_block)) + , m_top_right_block( + "top_right_block", + m_top_left_block->size(), + mat_size - m_top_left_block->size()) + , m_bottom_left_block("bottom_left_block", lambda_size1, lambda_size2) + , m_bottom_right_block( + new SplinesLinearProblemDense(mat_size - m_top_left_block->size())) + { + assert(m_top_left_block->size() <= mat_size); + + Kokkos::deep_copy(m_top_right_block.h_view, 0.); + Kokkos::deep_copy(m_bottom_left_block.h_view, 0.); + } + double get_element(std::size_t const i, std::size_t const j) const override { assert(i < size()); @@ -175,7 +203,7 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem * @param LinOp * @param transpose */ - void gemv_minus1_1( + virtual void gemv_minus1_1( MultiRHS const x, MultiRHS const y, Kokkos::View const diff --git a/include/ddc/kernels/splines/splines_linear_problem_maker.hpp b/include/ddc/kernels/splines/splines_linear_problem_maker.hpp index 3823ac89c..f192ba2e3 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_maker.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_maker.hpp @@ -12,6 +12,7 @@ #include "splines_linear_problem_dense.hpp" #include "splines_linear_problem_pds_band.hpp" #include "splines_linear_problem_pds_tridiag.hpp" +#include "splines_linear_problem_periodic_band.hpp" #include "splines_linear_problem_sparse.hpp" namespace ddc::detail { @@ -93,6 +94,44 @@ class SplinesLinearProblemMaker SplinesLinearProblem2x2Blocks>(n, std::move(top_left_block)); } + /** + * @brief Construct a 2x2-blocks linear problem with band "main" block (the one called + * Q in SplinesLinearProblem2x2Blocks). + * + * @tparam the Kokkos::ExecutionSpace on which matrix-related operation will be performed. + * @param n The size of one of the dimensions of the whole square matrix. + * @param kl The number of subdiagonals in the band block. + * @param ku The number of superdiagonals in the band block. + * @param pds A boolean indicating if the band block is positive-definite symetric or not. + * @param bottom_right_size The size of one of the dimensions of the bottom-right block. + * + * @return The SplinesLinearProblem instance. + */ + template + static std::unique_ptr> make_new_periodic_band_matrix( + int const n, + int const kl, + int const ku, + bool const pds) + { + int const bottom_size = std::max(kl, ku); + int const top_size = n - bottom_size; + std::unique_ptr> top_left_block; + if (bottom_size * n + bottom_size * (bottom_size + 1) + (2 * kl + 1 + ku) * top_size + >= n * n) { + return std::make_unique>(n); + } else if (pds && kl == ku && kl == 1) { + top_left_block = std::make_unique>(top_size); + } else if (kl == ku && pds) { + top_left_block = std::make_unique>(top_size, kl); + } else { + top_left_block + = std::make_unique>(top_size, kl, ku); + } + return std::make_unique< + SplinesLinearProblemPeriodicBand>(n, kl, ku, std::move(top_left_block)); + } + /** * @brief Construct a sparse matrix * diff --git a/include/ddc/kernels/splines/splines_linear_problem_periodic_band.hpp b/include/ddc/kernels/splines/splines_linear_problem_periodic_band.hpp index f1da6beac..94ffd370a 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_periodic_band.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_periodic_band.hpp @@ -40,6 +40,11 @@ class SplinesLinearProblemPeriodicBand : public SplinesLinearProblem2x2Blocks::m_top_left_block; + using SplinesLinearProblem2x2Blocks::m_top_right_block; + using SplinesLinearProblem2x2Blocks::m_bottom_left_block; + using SplinesLinearProblem2x2Blocks::m_bottom_right_block; + using SplinesLinearProblem2x2Blocks::gemv_minus1_1; public: /** @@ -53,7 +58,13 @@ class SplinesLinearProblemPeriodicBand : public SplinesLinearProblem2x2Blocks> top_left_block) - : SplinesLinearProblem2x2Blocks(mat_size, std::move(top_left_block)) + : SplinesLinearProblem2x2Blocks( + mat_size, + std::move(top_left_block), + std::max(kl, ku), + std::max(kl, ku) + 1) + , m_kl(kl) + , m_ku(ku) { } @@ -65,7 +76,7 @@ class SplinesLinearProblemPeriodicBand : public SplinesLinearProblem2x2Blockssize(); std::size_t const ndelta = m_bottom_right_block->size(); if (i >= nq && j < nq) { - std::size_t const d = j - i; + std::size_t d = j - i; if (d > size() / 2) d -= size(); if (d < -size() / 2) @@ -74,12 +85,12 @@ class SplinesLinearProblemPeriodicBand : public SplinesLinearProblem2x2Blocks m_ku) return 0.0; if (d > 0) { - return m_bottom_left_block(i - nq, j); + return m_bottom_left_block.h_view(i - nq, j); } else { - return m_bottom_left_block(i - nq, j - nq + ndelta + 1); + return m_bottom_left_block.h_view(i - nq, j - nq + ndelta + 1); } } else { - return MatrixCornerBlock::get_element(i, j); + return SplinesLinearProblem2x2Blocks::get_element(i, j); } } @@ -91,24 +102,24 @@ class SplinesLinearProblemPeriodicBand : public SplinesLinearProblem2x2Blockssize(); std::size_t const ndelta = m_bottom_right_block->size(); if (i >= nq && j < nq) { - int d = j - i; + std::size_t d = j - i; if (d > size() / 2) d -= size(); if (d < -size() / 2) d += size(); if (d < -m_kl || d > m_ku) { - assert(std::fabs(aij) < 1e-20); + // assert(std::fabs(aij) < 1e-20); return; } if (d > 0) { - m_bottom_left_block(i - nq, j) = aij; + m_bottom_left_block.h_view(i - nq, j) = aij; } else { - m_bottom_left_block(i - nq, j - nq + ndelta + 1) = aij; + m_bottom_left_block.h_view(i - nq, j - nq + ndelta + 1) = aij; } } else { - MatrixCornerBlock::set_element(i, j, aij); + SplinesLinearProblem2x2Blocks::set_element(i, j, aij); } } @@ -139,6 +150,7 @@ class SplinesLinearProblemPeriodicBand : public SplinesLinearProblem2x2Blocks const LinOp, bool const transpose = false) const { + /* assert(!transpose && LinOp.extent(0) == y.extent(0) || transpose && LinOp.extent(1) == y.extent(0)); assert(!transpose && LinOp.extent(1) == x.extent(0) || transpose && LinOp.extent(0) == x.extent(0)); + */ assert(x.extent(1) == y.extent(1)); + std::size_t const nq = m_top_left_block->size(); + std::size_t const ndelta = m_bottom_right_block->size(); Kokkos::parallel_for( - "gemv_minus1_1", + "per_gemv_minus1_1", Kokkos::TeamPolicy(y.extent(0) * y.extent(1), Kokkos::AUTO), KOKKOS_LAMBDA( const typename Kokkos::TeamPolicy::member_type& teamMember) { @@ -189,8 +205,7 @@ class SplinesLinearProblemPeriodicBand : public SplinesLinearProblem2x2Blockssize() - 1 - - m_bottom_right_block->size() + l; + int const l_full = nq - 1 - ndelta + l; if (!transpose) { LinOpTimesX_tmp += LinOp(i, l) * x(l_full, j); } else { @@ -203,6 +218,49 @@ class SplinesLinearProblemPeriodicBand : public SplinesLinearProblem2x2Blocks(0, m_top_left_block->size()), + Kokkos::ALL); + MultiRHS b2 = Kokkos:: + subview(b, + std::pair(m_top_left_block->size(), b.extent(0)), + Kokkos::ALL); + if (!transpose) { + m_top_left_block->solve(b1); + per_gemv_minus1_1(b1, b2, m_bottom_left_block.d_view); + m_bottom_right_block->solve(b2); + gemv_minus1_1(b2, b1, m_top_right_block.d_view); + } else { + gemv_minus1_1(b1, b2, m_top_right_block.d_view, true); + m_bottom_right_block->solve(b2, true); + per_gemv_minus1_1(b2, b1, m_bottom_left_block.d_view, true); + m_top_left_block->solve(b1, true); + } + } }; } // namespace ddc::detail diff --git a/tests/splines/matrix.cpp b/tests/splines/matrix.cpp index 7498da566..88bd33176 100644 --- a/tests/splines/matrix.cpp +++ b/tests/splines/matrix.cpp @@ -248,6 +248,31 @@ TEST(Matrix, 2x2Blocks) solve_and_validate(*matrix); } +TEST(Matrix, PeriodicBand) +{ + std::size_t const N = 10; + std::size_t const k = 3; + std::unique_ptr> top_left_block + = std::make_unique>(N - k, k, k); + std::unique_ptr> matrix + = std::make_unique>(N, k, k, std::move(top_left_block)); + + // Build a periodic band full-rank matrix + for (std::size_t i(0); i < N; ++i) { + for (std::size_t j(0); j < N; ++j) { + std::size_t diag = ((std::ptrdiff_t)j - (std::ptrdiff_t)i) % (std::ptrdiff_t)N; + if (diag == 0 || diag == N) { + matrix->set_element(i, j, 0.5); + } else if (diag <= k || diag >= N - k) { + matrix->set_element(i, j, -1.0 / k); + } + } + } + + solve_and_validate(*matrix); +} class MatrixSizesFixture : public testing::TestWithParam> { @@ -339,6 +364,35 @@ TEST_P(MatrixSizesFixture, 2x2Blocks) solve_and_validate(*matrix); } +TEST_P(MatrixSizesFixture, PeriodicBand) +{ + auto const [N, k] = GetParam(); + + // Build a non-symmetric full-rank band matrix + for (std::ptrdiff_t s(-k); s < (std::ptrdiff_t)k + 1; ++s) { + if (s == 0) + continue; + + std::unique_ptr> matrix + = ddc::detail::SplinesLinearProblemMaker::make_new_periodic_band_matrix< + Kokkos::DefaultExecutionSpace>(N, k - s, k + s, false); + for (std::size_t i(0); i < N; ++i) { + for (std::size_t j(0); j < N; ++j) { + int diag = ddc::detail::modulo((int)(j - i), (int)N); + if (diag == s || diag == (std::ptrdiff_t)N + s) { + matrix->set_element(i, j, 0.5); + } else if ( + diag <= s + (std::ptrdiff_t)k + || diag >= (std::ptrdiff_t)N + s - (std::ptrdiff_t)k) { + matrix->set_element(i, j, -1.0 / k); + } + } + } + + solve_and_validate(*matrix); + } +} + TEST_P(MatrixSizesFixture, Sparse) { auto const [N, k] = GetParam(); From ab80779e7661f3615049dd09b8974306975a473f Mon Sep 17 00:00:00 2001 From: blegouix Date: Mon, 3 Jun 2024 15:33:32 +0200 Subject: [PATCH 110/189] wip on a fix --- .../splines_linear_problem_periodic_band.hpp | 83 ++++++++++--------- tests/splines/matrix.cpp | 2 +- 2 files changed, 44 insertions(+), 41 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_periodic_band.hpp b/include/ddc/kernels/splines/splines_linear_problem_periodic_band.hpp index 94ffd370a..43ec8b02d 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_periodic_band.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_periodic_band.hpp @@ -76,15 +76,15 @@ class SplinesLinearProblemPeriodicBand : public SplinesLinearProblem2x2Blockssize(); std::size_t const ndelta = m_bottom_right_block->size(); if (i >= nq && j < nq) { - std::size_t d = j - i; - if (d > size() / 2) + std::ptrdiff_t d = j - i; + if (d > (std::ptrdiff_t)(size() / 2)) d -= size(); - if (d < -size() / 2) + if (d < -(std::ptrdiff_t)(size() / 2)) d += size(); - if (d < -m_kl || d > m_ku) + if (d < -(std::ptrdiff_t)m_kl || d > (std::ptrdiff_t)m_ku) return 0.0; - if (d > 0) { + if (d > (std::ptrdiff_t)0) { return m_bottom_left_block.h_view(i - nq, j); } else { return m_bottom_left_block.h_view(i - nq, j - nq + ndelta + 1); @@ -102,23 +102,23 @@ class SplinesLinearProblemPeriodicBand : public SplinesLinearProblem2x2Blockssize(); std::size_t const ndelta = m_bottom_right_block->size(); if (i >= nq && j < nq) { - std::size_t d = j - i; - if (d > size() / 2) + std::ptrdiff_t d = j - i; + if (d > (std::ptrdiff_t)(size() / 2)) d -= size(); - if (d < -size() / 2) + if (d < -(std::ptrdiff_t)(size() / 2)) d += size(); - if (d < -m_kl || d > m_ku) { - // assert(std::fabs(aij) < 1e-20); + if (d < -(std::ptrdiff_t)m_kl || d > (std::ptrdiff_t)m_ku) { + assert(std::fabs(aij) < 1e-20); return; } - - if (d > 0) { + if (d > (std::ptrdiff_t)0) { m_bottom_left_block.h_view(i - nq, j) = aij; } else { m_bottom_left_block.h_view(i - nq, j - nq + ndelta + 1) = aij; } } else { + printf("%i %i \n", i, j); SplinesLinearProblem2x2Blocks::set_element(i, j, aij); } } @@ -180,41 +180,44 @@ class SplinesLinearProblemPeriodicBand : public SplinesLinearProblem2x2Blockssize(); Kokkos::parallel_for( "per_gemv_minus1_1", - Kokkos::TeamPolicy(y.extent(0) * y.extent(1), Kokkos::AUTO), + Kokkos::TeamPolicy((y.extent(0) + transpose) * y.extent(1), Kokkos::AUTO), KOKKOS_LAMBDA( const typename Kokkos::TeamPolicy::member_type& teamMember) { const int i = teamMember.league_rank() / y.extent(1); const int j = teamMember.league_rank() % y.extent(1); - double LinOpTimesX = 0.; - Kokkos::parallel_reduce( - Kokkos::TeamThreadRange(teamMember, !transpose ? i + 1 : i), - [&](const int l, double& LinOpTimesX_tmp) { - if (!transpose) { + if (!transpose) { + double LinOpTimesX = 0.; + Kokkos::parallel_reduce( + Kokkos::TeamThreadRange(teamMember, i + 1), + [&](const int l, double& LinOpTimesX_tmp) { LinOpTimesX_tmp += LinOp(i, l) * x(l, j); - } else { - LinOpTimesX_tmp += LinOp(l, i) * x(l, j); - } - }, - LinOpTimesX); - teamMember.team_barrier(); - double LinOpTimesX2 = 0.; - Kokkos::parallel_reduce( - Kokkos::TeamThreadRange( - teamMember, - !transpose ? i + 1 : i, - x.extent(0)), - [&](const int l, double& LinOpTimesX_tmp) { - int const l_full = nq - 1 - ndelta + l; - if (!transpose) { + }, + LinOpTimesX); + teamMember.team_barrier(); + double LinOpTimesX2 = 0.; + Kokkos::parallel_reduce( + Kokkos::TeamThreadRange( + teamMember, + i + 1, + ndelta), + [&](const int l, double& LinOpTimesX_tmp) { + int const l_full = nq - 1 - ndelta + l; LinOpTimesX_tmp += LinOp(i, l) * x(l_full, j); - } else { - LinOpTimesX_tmp += LinOp(l, i) * x(l_full, j); - } - }, - LinOpTimesX2); - if (teamMember.team_rank() == 0) { - y(i, j) -= LinOpTimesX + LinOpTimesX2; + }, + LinOpTimesX2); + if (teamMember.team_rank() == 0) { + y(i, j) -= LinOpTimesX + LinOpTimesX2; + } + } else { + // Lower diagonals in lambda + for (int l = 0; l < i; ++l) { + y(nq - 1 - ndelta + i, j) -= LinOp(l, i) * x(l, j); + } + /// Upper diagonals in lambda + for (int l = i; l < ndelta; ++l) { + y(i, j) -= LinOp(l, i) * x(l, j); + } } }); } diff --git a/tests/splines/matrix.cpp b/tests/splines/matrix.cpp index 88bd33176..7fccb0142 100644 --- a/tests/splines/matrix.cpp +++ b/tests/splines/matrix.cpp @@ -262,7 +262,7 @@ TEST(Matrix, PeriodicBand) // Build a periodic band full-rank matrix for (std::size_t i(0); i < N; ++i) { for (std::size_t j(0); j < N; ++j) { - std::size_t diag = ((std::ptrdiff_t)j - (std::ptrdiff_t)i) % (std::ptrdiff_t)N; + std::size_t diag = std::abs((std::ptrdiff_t)j - (std::ptrdiff_t)i) % N; if (diag == 0 || diag == N) { matrix->set_element(i, j, 0.5); } else if (diag <= k || diag >= N - k) { From 30b93d41b875290593124a33ddaee01fc93269d2 Mon Sep 17 00:00:00 2001 From: blegouix Date: Mon, 3 Jun 2024 17:24:31 +0200 Subject: [PATCH 111/189] wip on making it work --- .../splines_linear_problem_periodic_band.hpp | 17 +++++++++-------- 1 file changed, 9 insertions(+), 8 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_periodic_band.hpp b/include/ddc/kernels/splines/splines_linear_problem_periodic_band.hpp index 43ec8b02d..b92418813 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_periodic_band.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_periodic_band.hpp @@ -118,7 +118,6 @@ class SplinesLinearProblemPeriodicBand : public SplinesLinearProblem2x2Blocks::set_element(i, j, aij); } } @@ -180,7 +179,8 @@ class SplinesLinearProblemPeriodicBand : public SplinesLinearProblem2x2Blockssize(); Kokkos::parallel_for( "per_gemv_minus1_1", - Kokkos::TeamPolicy((y.extent(0) + transpose) * y.extent(1), Kokkos::AUTO), + Kokkos::TeamPolicy< + ExecSpace>((y.extent(0) + transpose) * y.extent(1), Kokkos::AUTO), KOKKOS_LAMBDA( const typename Kokkos::TeamPolicy::member_type& teamMember) { const int i = teamMember.league_rank() / y.extent(1); @@ -197,10 +197,7 @@ class SplinesLinearProblemPeriodicBand : public SplinesLinearProblem2x2Blocks Date: Tue, 4 Jun 2024 14:28:59 +0200 Subject: [PATCH 112/189] init --- .../splines/splines_linear_problem_maker.hpp | 33 +++++++++++++++++ tests/splines/matrix.cpp | 35 +++++++++++++++++++ 2 files changed, 68 insertions(+) diff --git a/include/ddc/kernels/splines/splines_linear_problem_maker.hpp b/include/ddc/kernels/splines/splines_linear_problem_maker.hpp index 3823ac89c..38db17e64 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_maker.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_maker.hpp @@ -93,6 +93,39 @@ class SplinesLinearProblemMaker SplinesLinearProblem2x2Blocks>(n, std::move(top_left_block)); } + /** + * @brief Construct a 2x2-blocks linear problem with band "main" block (the one called + * Q in SplinesLinearProblem2x2Blocks) and other blocks containing the "periodic parts" of + * a periodic band matrix. + * + * It simply calls make_new_block_matrix_with_band_main_block with bottom_size being + * max(kl, ku) (except if the band part is too small, then the entire matrix is stored as dense). + * + * @tparam the Kokkos::ExecutionSpace on which matrix-related operation will be performed. + * @param n The size of one of the dimensions of the whole square matrix. + * @param kl The number of subdiagonals in the band block. + * @param ku The number of superdiagonals in the band block. + * @param pds A boolean indicating if the band block is positive-definite symetric or not. + * + * @return The SplinesLinearProblem instance. + */ + template + static std::unique_ptr> make_new_periodic_band_matrix( + int const n, + int const kl, + int const ku, + bool const pds) + { + int const bottom_size = std::max(kl, ku); + int const top_size = n - bottom_size; + + if (bottom_size > top_size) { + return std::make_unique>(n); + } + + return make_new_block_matrix_with_band_main_block(n, kl, ku, pds, bottom_size); + } + /** * @brief Construct a sparse matrix * diff --git a/tests/splines/matrix.cpp b/tests/splines/matrix.cpp index 7498da566..300b2ecd0 100644 --- a/tests/splines/matrix.cpp +++ b/tests/splines/matrix.cpp @@ -339,6 +339,41 @@ TEST_P(MatrixSizesFixture, 2x2Blocks) solve_and_validate(*matrix); } +TEST_P(MatrixSizesFixture, PeriodicBand) +{ + auto const [N, k] = GetParam(); + + // Build a positive-definite symmetric full-rank band matrix permuted in such a way the band is shifted + for (std::ptrdiff_t s(-(std::ptrdiff_t)k + (std::ptrdiff_t)k / 2 + 1); + s < (std::ptrdiff_t)k - (std::ptrdiff_t)k / 2; + ++s) { + if (s == 0) + continue; + + std::unique_ptr> matrix + = ddc::detail::SplinesLinearProblemMaker::make_new_periodic_band_matrix< + Kokkos::DefaultExecutionSpace>( + N, + (std::ptrdiff_t)k - s, + (std::ptrdiff_t)k + s, + false); + for (std::size_t i(0); i < N; ++i) { + for (std::size_t j(0); j < N; ++j) { + std::ptrdiff_t diag = ddc::detail::modulo((int)(j - i), (int)N); + if ((std::ptrdiff_t)diag == s || (std::ptrdiff_t)diag == (std::ptrdiff_t)N + s) { + matrix->set_element(i, j, 3. / 4); + } else if ( + (std::ptrdiff_t)diag <= s + (std::ptrdiff_t)k + || (std::ptrdiff_t)diag >= (std::ptrdiff_t)N + s - (std::ptrdiff_t)k) { + matrix->set_element(i, j, -1. / 4 / k); + } + } + } + + solve_and_validate(*matrix); + } +} + TEST_P(MatrixSizesFixture, Sparse) { auto const [N, k] = GetParam(); From 3b0933c1af86af42461b78f03eacbcb2df2dfe60 Mon Sep 17 00:00:00 2001 From: Baptiste Legouix Date: Tue, 4 Jun 2024 15:04:42 +0200 Subject: [PATCH 113/189] Apply suggestions from code review Co-authored-by: Thomas Padioleau --- .../splines/splines_linear_problem_2x2_blocks.hpp | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp index 89de9ba61..d56cd563d 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp @@ -50,7 +50,7 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem * @brief SplinesLinearProblem2x2Blocks constructor. * * @param mat_size The size of one of the dimensions of the square matrix. - * @param q A pointer toward the top-left SplinesLinearProblem. + * @param top_left_block A pointer toward the top-left SplinesLinearProblem. `setup_solver` must not have been called on `q`. */ explicit SplinesLinearProblem2x2Blocks( std::size_t const mat_size, @@ -109,7 +109,7 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem } private: - // @brief Compute the Schur complement delta - lambda*Q^-1*gamma. + /// @brief Compute the Schur complement delta - lambda*Q^-1*gamma. void compute_schur_complement() { Kokkos::parallel_for( @@ -180,10 +180,10 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem LinOp, bool const transpose = false) const { - assert(!transpose && LinOp.extent(0) == y.extent(0) - || transpose && LinOp.extent(1) == y.extent(0)); - assert(!transpose && LinOp.extent(1) == x.extent(0) - || transpose && LinOp.extent(0) == x.extent(0)); + assert((!transpose && LinOp.extent(0) == y.extent(0)) + || (transpose && LinOp.extent(1) == y.extent(0))); + assert((!transpose && LinOp.extent(1) == x.extent(0)) + || (transpose && LinOp.extent(0) == x.extent(0))); assert(x.extent(1) == y.extent(1)); Kokkos::parallel_for( From 398f6789f0221b3adbf9f8ea62c9a63de6f78f85 Mon Sep 17 00:00:00 2001 From: Baptiste Legouix Date: Tue, 4 Jun 2024 15:19:34 +0200 Subject: [PATCH 114/189] Apply suggestions from code review Co-authored-by: Thomas Padioleau --- .../ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp index d56cd563d..0c9b8bde6 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp @@ -205,9 +205,7 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem } }, LinOpTimesX); - if (teamMember.team_rank() == 0) { - y(i, j) -= LinOpTimesX; - } + Kokkos::single(Kokkos::PerTeam(team), [&]() { y(i, j) -= LinOpTimesX; }); }); } From 2e8fd7a4d4dd47c517e9994df2df016adf78994d Mon Sep 17 00:00:00 2001 From: blegouix Date: Tue, 4 Jun 2024 15:44:47 +0200 Subject: [PATCH 115/189] split gemv in two --- .../splines_linear_problem_2x2_blocks.hpp | 56 +++++++++++++------ 1 file changed, 38 insertions(+), 18 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp index 0c9b8bde6..a71132d13 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp @@ -186,27 +186,47 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem || (transpose && LinOp.extent(0) == x.extent(0))); assert(x.extent(1) == y.extent(1)); - Kokkos::parallel_for( - "gemv_minus1_1", - Kokkos::TeamPolicy(y.extent(0) * y.extent(1), Kokkos::AUTO), - KOKKOS_LAMBDA( - const typename Kokkos::TeamPolicy::member_type& teamMember) { - const int i = teamMember.league_rank() / y.extent(1); - const int j = teamMember.league_rank() % y.extent(1); + if (!transpose) { + Kokkos::parallel_for( + "gemv_minus1_1", + Kokkos::TeamPolicy(y.extent(0) * y.extent(1), Kokkos::AUTO), + KOKKOS_LAMBDA( + const typename Kokkos::TeamPolicy::member_type& teamMember) { + const int i = teamMember.league_rank() / y.extent(1); + const int j = teamMember.league_rank() % y.extent(1); - double LinOpTimesX = 0.; - Kokkos::parallel_reduce( - Kokkos::TeamThreadRange(teamMember, x.extent(0)), - [&](const int l, double& LinOpTimesX_tmp) { - if (!transpose) { + double LinOpTimesX = 0.; + Kokkos::parallel_reduce( + Kokkos::TeamThreadRange(teamMember, x.extent(0)), + [&](const int l, double& LinOpTimesX_tmp) { LinOpTimesX_tmp += LinOp(i, l) * x(l, j); - } else { + }, + LinOpTimesX); + Kokkos::single(Kokkos::PerTeam(teamMember), [&]() { + y(i, j) -= LinOpTimesX; + }); + }); + } else { + Kokkos::parallel_for( + "gemv_minus1_1_tr", + Kokkos::TeamPolicy(y.extent(0) * y.extent(1), Kokkos::AUTO), + KOKKOS_LAMBDA( + const typename Kokkos::TeamPolicy::member_type& teamMember) { + const int i = teamMember.league_rank() / y.extent(1); + const int j = teamMember.league_rank() % y.extent(1); + + double LinOpTimesX = 0.; + Kokkos::parallel_reduce( + Kokkos::TeamThreadRange(teamMember, x.extent(0)), + [&](const int l, double& LinOpTimesX_tmp) { LinOpTimesX_tmp += LinOp(l, i) * x(l, j); - } - }, - LinOpTimesX); - Kokkos::single(Kokkos::PerTeam(team), [&]() { y(i, j) -= LinOpTimesX; }); - }); + }, + LinOpTimesX); + Kokkos::single(Kokkos::PerTeam(teamMember), [&]() { + y(i, j) -= LinOpTimesX; + }); + }); + } } /** From 370d71e256b2314cc3d3357e9d6ce16cf1d62421 Mon Sep 17 00:00:00 2001 From: Baptiste Legouix Date: Tue, 4 Jun 2024 18:03:11 +0200 Subject: [PATCH 116/189] Update include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp Co-authored-by: Thomas Padioleau --- .../ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp index a71132d13..c459166fb 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp @@ -16,7 +16,7 @@ namespace ddc::detail { /** - * @brief A 2x2-blocks linear problem dedicated to the computation of a spline approximation (taking in account boundary conditions), + * @brief A 2x2-blocks linear problem dedicated to the computation of a spline approximation, * with all blocks except top-left one being stored in dense format. * * A = | Q | gamma | From 59a42298088055b3951daf513a2067a45789c2fb Mon Sep 17 00:00:00 2001 From: blegouix Date: Tue, 4 Jun 2024 18:25:43 +0200 Subject: [PATCH 117/189] fixes --- .../splines/splines_linear_problem_maker.hpp | 6 +++--- tests/splines/matrix.cpp | 20 +++++++------------ 2 files changed, 10 insertions(+), 16 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_maker.hpp b/include/ddc/kernels/splines/splines_linear_problem_maker.hpp index 38db17e64..541b43858 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_maker.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_maker.hpp @@ -99,7 +99,7 @@ class SplinesLinearProblemMaker * a periodic band matrix. * * It simply calls make_new_block_matrix_with_band_main_block with bottom_size being - * max(kl, ku) (except if the band part is too small, then the entire matrix is stored as dense). + * max(kl, ku) (except if the alloation would be higher than instantiating a SplinesLinearProblemDense). * * @tparam the Kokkos::ExecutionSpace on which matrix-related operation will be performed. * @param n The size of one of the dimensions of the whole square matrix. @@ -117,9 +117,9 @@ class SplinesLinearProblemMaker bool const pds) { int const bottom_size = std::max(kl, ku); - int const top_size = n - bottom_size; + int const top_size = std::max(0, n - bottom_size); - if (bottom_size > top_size) { + if (bottom_size * (n + top_size) + (2 * kl + ku + 1) * top_size >= n * n) { return std::make_unique>(n); } diff --git a/tests/splines/matrix.cpp b/tests/splines/matrix.cpp index 300b2ecd0..df94f8eed 100644 --- a/tests/splines/matrix.cpp +++ b/tests/splines/matrix.cpp @@ -344,12 +344,7 @@ TEST_P(MatrixSizesFixture, PeriodicBand) auto const [N, k] = GetParam(); // Build a positive-definite symmetric full-rank band matrix permuted in such a way the band is shifted - for (std::ptrdiff_t s(-(std::ptrdiff_t)k + (std::ptrdiff_t)k / 2 + 1); - s < (std::ptrdiff_t)k - (std::ptrdiff_t)k / 2; - ++s) { - if (s == 0) - continue; - + for (std::ptrdiff_t s(-k); s < (std::ptrdiff_t)k + 1; ++s) { std::unique_ptr> matrix = ddc::detail::SplinesLinearProblemMaker::make_new_periodic_band_matrix< Kokkos::DefaultExecutionSpace>( @@ -359,13 +354,12 @@ TEST_P(MatrixSizesFixture, PeriodicBand) false); for (std::size_t i(0); i < N; ++i) { for (std::size_t j(0); j < N; ++j) { - std::ptrdiff_t diag = ddc::detail::modulo((int)(j - i), (int)N); - if ((std::ptrdiff_t)diag == s || (std::ptrdiff_t)diag == (std::ptrdiff_t)N + s) { - matrix->set_element(i, j, 3. / 4); - } else if ( - (std::ptrdiff_t)diag <= s + (std::ptrdiff_t)k - || (std::ptrdiff_t)diag >= (std::ptrdiff_t)N + s - (std::ptrdiff_t)k) { - matrix->set_element(i, j, -1. / 4 / k); + std::ptrdiff_t diag + = ddc::detail::modulo((std::ptrdiff_t)(j - i), (std::ptrdiff_t)N); + if (diag == s || diag == N + s) { + matrix->set_element(i, j, .5); + } else if (diag <= s + k || diag >= N + s - k) { + matrix->set_element(i, j, -1. / k); } } } From 59e48348ebc988c57d1ad6dfb46cda444b7ed856 Mon Sep 17 00:00:00 2001 From: blegouix Date: Tue, 4 Jun 2024 18:35:12 +0200 Subject: [PATCH 118/189] minor --- tests/splines/matrix.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/splines/matrix.cpp b/tests/splines/matrix.cpp index df94f8eed..ba0d1fe69 100644 --- a/tests/splines/matrix.cpp +++ b/tests/splines/matrix.cpp @@ -343,7 +343,7 @@ TEST_P(MatrixSizesFixture, PeriodicBand) { auto const [N, k] = GetParam(); - // Build a positive-definite symmetric full-rank band matrix permuted in such a way the band is shifted + // Build a full-rank periodic band matrix permuted in such a way the band is shifted for (std::ptrdiff_t s(-k); s < (std::ptrdiff_t)k + 1; ++s) { std::unique_ptr> matrix = ddc::detail::SplinesLinearProblemMaker::make_new_periodic_band_matrix< From a5b2cc23dc09353631c517d45e3af667533be50d Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 5 Jun 2024 12:57:01 +0200 Subject: [PATCH 119/189] init --- .../splines_linear_problem_3x3_blocks.hpp | 188 ++++++++++++++++++ 1 file changed, 188 insertions(+) create mode 100644 include/ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp diff --git a/include/ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp new file mode 100644 index 000000000..141934304 --- /dev/null +++ b/include/ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp @@ -0,0 +1,188 @@ +// Copyright (C) The DDC development team, see COPYRIGHT.md file +// +// SPDX-License-Identifier: MIT + +#pragma once + +#include +#include +#include + +#include + +#include "splines_linear_problem.hpp" +#include "splines_linear_problem_2x2_blocks.hpp" + +namespace ddc::detail { + +/** + * @brief A 3x3-blocks linear problem dedicated to the computation of a spline approximation, + * with all blocks except center one being stored in dense format. + * + * A = | a | b | c | + * | d | Q | e | + * | f | g | h | + * + * The storage format is dense for all blocks except center one, whose storage format is determined by its type. + * + * This class implements row & columns interchanges of the matrix and of multiple right-hand sides to restructure the + * 3x3-blocks linear problem into a 2x2-blocks linear problem, relying then on the operations implemented in SplinesLinearProblem2x2Blocks. + * + * @tparam ExecSpace The Kokkos::ExecutionSpace on which operations related to the matrix are supposed to be performed. + */ +template +class SplinesLinearProblem3x3Blocks : public SplinesLinearProblem2x2Blocks +{ +public: + using typename SplinesLinearProblem2x2Blocks::MultiRHS; + using SplinesLinearProblem2x2Blocks::size; + using SplinesLinearProblem2x2Blocks::solve; + using SplinesLinearProblem2x2Blocks::m_top_left_block; + using SplinesLinearProblem2x2Blocks::m_top_right_block; + using SplinesLinearProblem2x2Blocks::m_bottom_left_block; + using SplinesLinearProblem2x2Blocks::m_bottom_right_block; + +protected: + std::size_t m_top_size; + +public: + /** + * @brief SplinesLinearProblem3x3Blocks constructor. + * + * @param top_size The size of one of the dimensions of the top-left block. + * @param center_block A pointer toward the center SplinesLinearProblem. `setup_solver` must not have been called on it. + * @param bottom_size The size of one of the dimensions of the bottom-right block. + */ + explicit SplinesLinearProblem3x3Blocks( + std::size_t const mat_size, + std::size_t const top_size, + std::unique_ptr> center_block) + : SplinesLinearProblem2x2Blocks(mat_size, std::move(center_block)) + , m_top_size(top_size) + { + } + +private: + /// @brief Adjust indexes, governs the row & columns interchanges to restructure the 3x3-blocks matrix into a 2x2-blocks matrix. + void adjust_indexes(std::size_t& i, std::size_t& j) const + { + std::size_t nq = m_top_left_block->size(); // size of the center block + + if (i < m_top_size) + i += nq; + else if (i < m_top_size + nq) + i -= m_top_size; + + if (j < m_top_size) + j += nq; + else if (j < m_top_size + nq) + j -= m_top_size; + } + +public: + double get_element(std::size_t i, std::size_t j) const override + { + adjust_indexes(i, j); + return SplinesLinearProblem2x2Blocks::get_element(i, j); + } + + void set_element(std::size_t i, std::size_t j, double const aij) override + { + adjust_indexes(i, j); + return SplinesLinearProblem2x2Blocks::set_element(i, j, aij); + } + +private: + /** + * @brief Performs row interchanges on multiple right-hand sides to give it a 2-blocks structure (matching the requirements + * of the SplinesLinearSolver2x2Blocks solver). + * + * | b_top | | b_center | + * | b_center | -> | b_top | -| Considered as a + * | b_bottom | | b_bottom | -| single bottom block + * + * @param b The multiple right-hand sides. + */ + void row_interchanges_from_3_to_2_blocks_rhs(MultiRHS b) const + { + std::size_t nq = m_top_left_block->size(); // size of the center block + + MultiRHS b_top = Kokkos:: + subview(b, std::pair {0, m_top_size}, Kokkos::ALL); + MultiRHS b_center = Kokkos:: + subview(b, + std::pair {m_top_size, m_top_size + nq}, + Kokkos::ALL); + MultiRHS b_bottom = Kokkos:: + subview(b, + std::pair {m_top_size + nq, size()}, + Kokkos::ALL); + + MultiRHS b_center_dst + = Kokkos::subview(b, std::pair {0, nq}, Kokkos::ALL); + MultiRHS b_top_dst = Kokkos:: + subview(b, std::pair {nq, nq + m_top_size}, Kokkos::ALL); + + MultiRHS buffer = Kokkos::create_mirror(ExecSpace(), b_center); + + Kokkos::deep_copy(buffer, b_center); + Kokkos::deep_copy(b_top_dst, b_top); + Kokkos::deep_copy(b_center_dst, buffer); + } + + /** + * @brief Performs row interchanges on multiple right-hand sides to restore the 3-blocks structure. + * + * | b_center | | b_top | + * | b_top | -> | b_center | + * | b_bottom | | b_bottom | + * + * @param b The multiple right-hand sides. + */ + void row_interchanges_from_2_to_3_blocks_rhs(MultiRHS b) const + { + std::size_t nq = m_top_left_block->size(); // size of the center block + + MultiRHS b_center_src + = Kokkos::subview(b, std::pair {0, nq}, Kokkos::ALL); + MultiRHS b_top_src = Kokkos:: + subview(b, std::pair {nq, nq + m_top_size}, Kokkos::ALL); + + MultiRHS b_top = Kokkos:: + subview(b, std::pair {0, m_top_size}, Kokkos::ALL); + MultiRHS b_center = Kokkos:: + subview(b, + std::pair {m_top_size, m_top_size + nq}, + Kokkos::ALL); + MultiRHS b_bottom = Kokkos:: + subview(b, + std::pair {m_top_size + nq, size()}, + Kokkos::ALL); + + MultiRHS buffer = Kokkos::create_mirror(ExecSpace(), b_center); + + Kokkos::deep_copy(buffer, b_center_src); + Kokkos::deep_copy(b_top, b_top_src); + Kokkos::deep_copy(b_center, buffer); + } + +public: + /** + * @brief Solve the multiple right-hand sides linear problem Ax=b or its transposed version A^tx=b inplace. + * + * Perform row interchanges on multiple right-hand sides to obtain a 2x2-blocks linear problem and call the SplinesLinearProblem2x2Blocks solver. + * + * @param[in, out] b A 2D Kokkos::View storing the multiple right-hand sides of the problem and receiving the corresponding solution. + * @param transpose Choose between the direct or transposed version of the linear problem. + */ + void solve(MultiRHS b, bool const transpose) const override + { + assert(b.extent(0) == size()); + + row_interchanges_from_3_to_2_blocks_rhs(b); + SplinesLinearProblem2x2Blocks::solve(b, transpose); + row_interchanges_from_2_to_3_blocks_rhs(b); + } +}; + +} // namespace ddc::detail From cc69eb264fc41ae4855e0b450169aadcdeeb66ca Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 5 Jun 2024 13:18:40 +0200 Subject: [PATCH 120/189] autoreview + missing files --- include/ddc/kernels/splines.hpp | 1 + .../splines_linear_problem_2x2_blocks.hpp | 2 +- .../splines_linear_problem_3x3_blocks.hpp | 57 +++++++++---------- .../splines/splines_linear_problem_maker.hpp | 23 +++++--- tests/splines/matrix.cpp | 48 +++++++++++++++- 5 files changed, 92 insertions(+), 39 deletions(-) diff --git a/include/ddc/kernels/splines.hpp b/include/ddc/kernels/splines.hpp index 1cae877fd..27595fecd 100644 --- a/include/ddc/kernels/splines.hpp +++ b/include/ddc/kernels/splines.hpp @@ -20,6 +20,7 @@ #include "splines/spline_evaluator_2d.hpp" #include "splines/splines_linear_problem.hpp" #include "splines/splines_linear_problem_2x2_blocks.hpp" +#include "splines/splines_linear_problem_3x3_blocks.hpp" #include "splines/splines_linear_problem_band.hpp" #include "splines/splines_linear_problem_dense.hpp" #include "splines/splines_linear_problem_maker.hpp" diff --git a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp index c459166fb..fe605d71d 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp @@ -50,7 +50,7 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem * @brief SplinesLinearProblem2x2Blocks constructor. * * @param mat_size The size of one of the dimensions of the square matrix. - * @param top_left_block A pointer toward the top-left SplinesLinearProblem. `setup_solver` must not have been called on `q`. + * @param top_left_block A pointer toward the top-left SplinesLinearProblem. `setup_solver` must not have been called on it. */ explicit SplinesLinearProblem2x2Blocks( std::size_t const mat_size, diff --git a/include/ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp index 141934304..97654887d 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp @@ -25,6 +25,8 @@ namespace ddc::detail { * * The storage format is dense for all blocks except center one, whose storage format is determined by its type. * + * The matrix itself and blocks a, Q and h are square (which fully determines the dimensions of the others). + * * This class implements row & columns interchanges of the matrix and of multiple right-hand sides to restructure the * 3x3-blocks linear problem into a 2x2-blocks linear problem, relying then on the operations implemented in SplinesLinearProblem2x2Blocks. * @@ -38,9 +40,6 @@ class SplinesLinearProblem3x3Blocks : public SplinesLinearProblem2x2Blocks::size; using SplinesLinearProblem2x2Blocks::solve; using SplinesLinearProblem2x2Blocks::m_top_left_block; - using SplinesLinearProblem2x2Blocks::m_top_right_block; - using SplinesLinearProblem2x2Blocks::m_bottom_left_block; - using SplinesLinearProblem2x2Blocks::m_bottom_right_block; protected: std::size_t m_top_size; @@ -49,9 +48,9 @@ class SplinesLinearProblem3x3Blocks : public SplinesLinearProblem2x2Blockssize(); // size of the center block + std::size_t const nq = m_top_left_block->size(); // size of the center block if (i < m_top_size) i += nq; @@ -94,36 +93,36 @@ class SplinesLinearProblem3x3Blocks : public SplinesLinearProblem2x2Blocks | b_top | -| Considered as a - * | b_bottom | | b_bottom | -| single bottom block + * | b_center | -> | b_top | -- Considered as a + * | b_bottom | | b_bottom | -- single bottom block * * @param b The multiple right-hand sides. */ - void row_interchanges_from_3_to_2_blocks_rhs(MultiRHS b) const + void interchange_rows_from_3_to_2_blocks_rhs(MultiRHS b) const { - std::size_t nq = m_top_left_block->size(); // size of the center block + std::size_t const nq = m_top_left_block->size(); // size of the center block - MultiRHS b_top = Kokkos:: + MultiRHS const b_top = Kokkos:: subview(b, std::pair {0, m_top_size}, Kokkos::ALL); - MultiRHS b_center = Kokkos:: + MultiRHS const b_center = Kokkos:: subview(b, std::pair {m_top_size, m_top_size + nq}, Kokkos::ALL); - MultiRHS b_bottom = Kokkos:: + MultiRHS const b_bottom = Kokkos:: subview(b, std::pair {m_top_size + nq, size()}, Kokkos::ALL); - MultiRHS b_center_dst + MultiRHS const b_center_dst = Kokkos::subview(b, std::pair {0, nq}, Kokkos::ALL); - MultiRHS b_top_dst = Kokkos:: + MultiRHS const b_top_dst = Kokkos:: subview(b, std::pair {nq, nq + m_top_size}, Kokkos::ALL); - MultiRHS buffer = Kokkos::create_mirror(ExecSpace(), b_center); + MultiRHS const buffer = Kokkos::create_mirror(ExecSpace(), b_center); Kokkos::deep_copy(buffer, b_center); Kokkos::deep_copy(b_top_dst, b_top); @@ -131,7 +130,7 @@ class SplinesLinearProblem3x3Blocks : public SplinesLinearProblem2x2Blocks | b_center | @@ -139,27 +138,27 @@ class SplinesLinearProblem3x3Blocks : public SplinesLinearProblem2x2Blockssize(); // size of the center block + std::size_t const nq = m_top_left_block->size(); // size of the center block - MultiRHS b_center_src + MultiRHS const b_center_src = Kokkos::subview(b, std::pair {0, nq}, Kokkos::ALL); - MultiRHS b_top_src = Kokkos:: + MultiRHS const b_top_src = Kokkos:: subview(b, std::pair {nq, nq + m_top_size}, Kokkos::ALL); - MultiRHS b_top = Kokkos:: + MultiRHS const b_top = Kokkos:: subview(b, std::pair {0, m_top_size}, Kokkos::ALL); - MultiRHS b_center = Kokkos:: + MultiRHS const b_center = Kokkos:: subview(b, std::pair {m_top_size, m_top_size + nq}, Kokkos::ALL); - MultiRHS b_bottom = Kokkos:: + MultiRHS const b_bottom = Kokkos:: subview(b, std::pair {m_top_size + nq, size()}, Kokkos::ALL); - MultiRHS buffer = Kokkos::create_mirror(ExecSpace(), b_center); + MultiRHS const buffer = Kokkos::create_mirror(ExecSpace(), b_center); Kokkos::deep_copy(buffer, b_center_src); Kokkos::deep_copy(b_top, b_top_src); @@ -179,9 +178,9 @@ class SplinesLinearProblem3x3Blocks : public SplinesLinearProblem2x2Blocks::solve(b, transpose); - row_interchanges_from_2_to_3_blocks_rhs(b); + interchange_rows_from_2_to_3_blocks_rhs(b); } }; diff --git a/include/ddc/kernels/splines/splines_linear_problem_maker.hpp b/include/ddc/kernels/splines/splines_linear_problem_maker.hpp index 3823ac89c..65d69b3a9 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_maker.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_maker.hpp @@ -8,6 +8,7 @@ #include #include "splines_linear_problem_2x2_blocks.hpp" +#include "splines_linear_problem_3x3_blocks.hpp" #include "splines_linear_problem_band.hpp" #include "splines_linear_problem_dense.hpp" #include "splines_linear_problem_pds_band.hpp" @@ -65,15 +66,16 @@ class SplinesLinearProblemMaker } /** - * @brief Construct a 2x2-blocks linear problem with band "main" block (the one called - * Q in SplinesLinearProblem2x2Blocks). + * @brief Construct a 2x2-blocks or 3x3-blocks linear problem with band "main" block (the one called + * Q in SplinesLinearProblem2x2Blocks and SplinesLinearProblem3x3Blocks). * * @tparam the Kokkos::ExecutionSpace on which matrix-related operation will be performed. * @param n The size of one of the dimensions of the whole square matrix. * @param kl The number of subdiagonals in the band block. * @param ku The number of superdiagonals in the band block. * @param pds A boolean indicating if the band block is positive-definite symetric or not. - * @param bottom_right_size The size of one of the dimensions of the bottom-right block. + * @param bottom_size The size of one of the dimensions of the bottom-right block. + * @param top_size The size of one of the dimensions of the top-left block. * * @return The SplinesLinearProblem instance. */ @@ -84,13 +86,18 @@ class SplinesLinearProblemMaker int const kl, int const ku, bool const pds, - int const bottom_size) + int const bottom_size, + int const top_size = 0) { - int const top_size = n - bottom_size; - std::unique_ptr> top_left_block - = make_new_band(top_size, kl, ku, pds); + int const main_size = n - bottom_size - top_size; + std::unique_ptr> main_block + = make_new_band(main_size, kl, ku, pds); + if (top_size == 0) { + return std::make_unique< + SplinesLinearProblem2x2Blocks>(n, std::move(main_block)); + } return std::make_unique< - SplinesLinearProblem2x2Blocks>(n, std::move(top_left_block)); + SplinesLinearProblem3x3Blocks>(n, top_size, std::move(main_block)); } /** diff --git a/tests/splines/matrix.cpp b/tests/splines/matrix.cpp index 7498da566..73c887ab6 100644 --- a/tests/splines/matrix.cpp +++ b/tests/splines/matrix.cpp @@ -229,7 +229,7 @@ TEST(Matrix, 2x2Blocks) std::size_t const k = 10; std::unique_ptr> top_left_block = std::make_unique< - ddc::detail::SplinesLinearProblemDense>(3); + ddc::detail::SplinesLinearProblemDense>(7); std::unique_ptr> matrix = std::make_unique>(N, std::move(top_left_block)); @@ -248,6 +248,31 @@ TEST(Matrix, 2x2Blocks) solve_and_validate(*matrix); } +TEST(Matrix, 3x3Blocks) +{ + std::size_t const N = 10; + std::size_t const k = 10; + std::unique_ptr> center_block + = std::make_unique< + ddc::detail::SplinesLinearProblemDense>(N - 5); + std::unique_ptr> matrix + = std::make_unique>(N, 2, std::move(center_block)); + + // Build a non-symmetric full-rank matrix (without zero) + for (std::size_t i(0); i < N; ++i) { + std::cout << i; + matrix->set_element(i, i, 3. / 4 * ((N + 1) * i + 1)); + for (std::size_t j(std::max(0, int(i) - int(k))); j < i; ++j) { + matrix->set_element(i, j, -(1. / 4) / k * (N * i + j + 1)); + } + for (std::size_t j(i + 1); j < std::min(N, i + k + 1); ++j) { + matrix->set_element(i, j, -(1. / 4) / k * (N * i + j + 1)); + } + } + + solve_and_validate(*matrix); +} class MatrixSizesFixture : public testing::TestWithParam> { @@ -339,6 +364,27 @@ TEST_P(MatrixSizesFixture, 2x2Blocks) solve_and_validate(*matrix); } +TEST_P(MatrixSizesFixture, 3x3Blocks) +{ + auto const [N, k] = GetParam(); + std::unique_ptr> matrix + = ddc::detail::SplinesLinearProblemMaker::make_new_block_matrix_with_band_main_block< + Kokkos::DefaultExecutionSpace>(N, k, k, false, 3, 2); + + // Build a non-symmetric full-rank band matrix + for (std::size_t i(0); i < N; ++i) { + matrix->set_element(i, i, 3. / 4 * ((N + 1) * i + 1)); + for (std::size_t j(std::max(0, int(i) - int(k))); j < i; ++j) { + matrix->set_element(i, j, -(1. / 4) / k * (N * i + j + 1)); + } + for (std::size_t j(i + 1); j < std::min(N, i + k + 1); ++j) { + matrix->set_element(i, j, -(1. / 4) / k * (N * i + j + 1)); + } + } + + solve_and_validate(*matrix); +} + TEST_P(MatrixSizesFixture, Sparse) { auto const [N, k] = GetParam(); From eac561be0d0ea29a0238be294fdd8a4fece67a8f Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 5 Jun 2024 13:28:52 +0200 Subject: [PATCH 121/189] autoreview --- .../splines/splines_linear_problem_maker.hpp | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_maker.hpp b/include/ddc/kernels/splines/splines_linear_problem_maker.hpp index 65d69b3a9..630aa2ee3 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_maker.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_maker.hpp @@ -74,8 +74,8 @@ class SplinesLinearProblemMaker * @param kl The number of subdiagonals in the band block. * @param ku The number of superdiagonals in the band block. * @param pds A boolean indicating if the band block is positive-definite symetric or not. - * @param bottom_size The size of one of the dimensions of the bottom-right block. - * @param top_size The size of one of the dimensions of the top-left block. + * @param bottom_right_size The size of one of the dimensions of the bottom-right square block. + * @param top_left_size The size of one of the dimensions of the top-left square block. * * @return The SplinesLinearProblem instance. */ @@ -86,18 +86,18 @@ class SplinesLinearProblemMaker int const kl, int const ku, bool const pds, - int const bottom_size, - int const top_size = 0) + int const bottom_right_size, + int const top_left_size = 0) { - int const main_size = n - bottom_size - top_size; + int const main_size = n - top_left_size - bottom_right_size; std::unique_ptr> main_block = make_new_band(main_size, kl, ku, pds); - if (top_size == 0) { + if (top_left_size == 0) { return std::make_unique< SplinesLinearProblem2x2Blocks>(n, std::move(main_block)); } return std::make_unique< - SplinesLinearProblem3x3Blocks>(n, top_size, std::move(main_block)); + SplinesLinearProblem3x3Blocks>(n, top_left_size, std::move(main_block)); } /** From 605c662b0e5001649b4f1af570559d6bf8b2bbe0 Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 5 Jun 2024 13:38:40 +0200 Subject: [PATCH 122/189] autoreview --- .../splines/splines_linear_problem_3x3_blocks.hpp | 14 ++++++-------- 1 file changed, 6 insertions(+), 8 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp index 97654887d..8c4d0f202 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp @@ -8,8 +8,6 @@ #include #include -#include - #include "splines_linear_problem.hpp" #include "splines_linear_problem_2x2_blocks.hpp" @@ -62,8 +60,8 @@ class SplinesLinearProblem3x3Blocks : public SplinesLinearProblem2x2Blockssize(); // size of the center block @@ -81,19 +79,19 @@ class SplinesLinearProblem3x3Blocks : public SplinesLinearProblem2x2Blocks::get_element(i, j); } void set_element(std::size_t i, std::size_t j, double const aij) override { - adjust_indexes(i, j); + adjust_indices(i, j); return SplinesLinearProblem2x2Blocks::set_element(i, j, aij); } private: /** - * @brief Performs row interchanges on multiple right-hand sides to get a 2-blocks structure (matching the requirements + * @brief Perform row interchanges on multiple right-hand sides to get a 2-blocks structure (matching the requirements * of the SplinesLinearProblem2x2Blocks solver). * * | b_top | | b_center | @@ -130,7 +128,7 @@ class SplinesLinearProblem3x3Blocks : public SplinesLinearProblem2x2Blocks | b_center | From b6cb5967f679ae8e6d9db18655999d8f5ae06699 Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 5 Jun 2024 15:27:32 +0200 Subject: [PATCH 123/189] init --- .../ddc/kernels/splines/spline_builder.hpp | 37 ++++++++++++++++--- tests/splines/CMakeLists.txt | 24 +++++++++++- tests/splines/batched_spline_builder.cpp | 32 ++++++++++------ 3 files changed, 74 insertions(+), 19 deletions(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index 4fac848af..c5b375f09 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -18,7 +18,8 @@ namespace ddc { * An enum determining the backend solver of a SplineBuilder or SplineBuilder2d. */ enum class SplineSolver { - GINKGO ///< Enum member to identify the Ginkgo-based solver (iterative method) + GINKGO, ///< Enum member to identify the Ginkgo-based solver (iterative method) + LAPACK ///< Enum member to identify the LAPACK-based solver (direct method) }; /** @@ -599,10 +600,36 @@ void SplineBuilder< return; */ - matrix = ddc::detail::SplinesLinearProblemMaker::make_new_sparse( - ddc::discrete_space().nbasis(), - cols_per_chunk, - preconditionner_max_block_size); + if constexpr (Solver == ddc::SplineSolver::LAPACK) { + int upper_band_width; + if (bsplines_type::is_uniform()) { + upper_band_width = bsplines_type::degree() / 2; + } else { + upper_band_width = bsplines_type::degree() - 1; + } + if constexpr (bsplines_type::is_periodic()) { + matrix = ddc::detail::SplinesLinearProblemMaker::make_new_periodic_band_matrix< + ExecSpace>( + ddc::discrete_space().nbasis(), + upper_band_width, + upper_band_width, + bsplines_type::is_uniform()); + } else { + matrix = ddc::detail::SplinesLinearProblemMaker:: + make_new_block_matrix_with_band_main_block( + ddc::discrete_space().nbasis(), + upper_band_width, + upper_band_width, + bsplines_type::is_uniform(), + lower_block_size, + upper_block_size); + } + } else if constexpr (Solver == ddc::SplineSolver::GINKGO) { + matrix = ddc::detail::SplinesLinearProblemMaker::make_new_sparse( + ddc::discrete_space().nbasis(), + cols_per_chunk, + preconditionner_max_block_size); + } build_matrix_system(); diff --git a/tests/splines/CMakeLists.txt b/tests/splines/CMakeLists.txt index 785d89819..ebc24f9b2 100644 --- a/tests/splines/CMakeLists.txt +++ b/tests/splines/CMakeLists.txt @@ -101,10 +101,11 @@ foreach(BC "BC_PERIODIC" "BC_GREVILLE") endforeach() endforeach() +# LAPACK foreach(BC "BC_PERIODIC" "BC_GREVILLE" "BC_HERMITE") foreach(DEGREE_X RANGE "${SPLINES_TEST_DEGREE_MIN}" "${SPLINES_TEST_DEGREE_MAX}") foreach(BSPLINES_TYPE "BSPLINES_TYPE_UNIFORM" "BSPLINES_TYPE_NON_UNIFORM") - set(test_name "splines_tests_BATCHED_DEGREE_X_${DEGREE_X}_${BSPLINES_TYPE}_${BC}") + set(test_name "splines_tests_BATCHED_DEGREE_X_${DEGREE_X}_${BSPLINES_TYPE}_${BC}_LAPACK") add_executable("${test_name}" ../main.cpp batched_spline_builder.cpp) target_compile_features("${test_name}" PUBLIC cxx_std_17) target_link_libraries("${test_name}" @@ -112,7 +113,26 @@ foreach(BC "BC_PERIODIC" "BC_GREVILLE" "BC_HERMITE") GTest::gtest DDC::DDC ) - target_compile_definitions("${test_name}" PUBLIC -DDEGREE_X=${DEGREE_X} -D${BSPLINES_TYPE} -D${BC}) + target_compile_definitions("${test_name}" PUBLIC -DDEGREE_X=${DEGREE_X} -D${BSPLINES_TYPE} -D${BC} -DSOLVER_LAPACK) + # add_test("${test_name}" "${test_name}") + gtest_discover_tests("${test_name}" DISCOVERY_MODE PRE_TEST) + endforeach() + endforeach() +endforeach() + +# GINKGO +foreach(BC "BC_PERIODIC") + foreach(DEGREE_X RANGE "${SPLINES_TEST_DEGREE_MIN}" "${SPLINES_TEST_DEGREE_MAX}") + foreach(BSPLINES_TYPE "BSPLINES_TYPE_UNIFORM" "BSPLINES_TYPE_NON_UNIFORM") + set(test_name "splines_tests_BATCHED_DEGREE_X_${DEGREE_X}_${BSPLINES_TYPE}_${BC}_GINKGO") + add_executable("${test_name}" ../main.cpp batched_spline_builder.cpp) + target_compile_features("${test_name}" PUBLIC cxx_std_17) + target_link_libraries("${test_name}" + PUBLIC + GTest::gtest + DDC::DDC + ) + target_compile_definitions("${test_name}" PUBLIC -DDEGREE_X=${DEGREE_X} -D${BSPLINES_TYPE} -D${BC} -DSOLVER_GINKGO) # add_test("${test_name}" "${test_name}") gtest_discover_tests("${test_name}" DISCOVERY_MODE PRE_TEST) endforeach() diff --git a/tests/splines/batched_spline_builder.cpp b/tests/splines/batched_spline_builder.cpp index a714b3660..31c57f054 100644 --- a/tests/splines/batched_spline_builder.cpp +++ b/tests/splines/batched_spline_builder.cpp @@ -231,7 +231,11 @@ static void BatchedSplineTest() IDim, s_bcl, s_bcr, +#if defined(SOLVER_LAPACK) + ddc::SplineSolver::LAPACK, +#elif defined(SOLVER_GINKGO) ddc::SplineSolver::GINKGO, +#endif IDim...> spline_builder(dom_vals); @@ -416,18 +420,22 @@ static void BatchedSplineTest() 1.0e-14 * max_norm_int)); } -#if defined(BC_PERIODIC) && defined(BSPLINES_TYPE_UNIFORM) -#define SUFFIX(name) name##Periodic##Uniform -#elif defined(BC_PERIODIC) && defined(BSPLINES_TYPE_NON_UNIFORM) -#define SUFFIX(name) name##Periodic##NonUniform -#elif defined(BC_GREVILLE) && defined(BSPLINES_TYPE_UNIFORM) -#define SUFFIX(name) name##Greville##Uniform -#elif defined(BC_GREVILLE) && defined(BSPLINES_TYPE_NON_UNIFORM) -#define SUFFIX(name) name##Greville##NonUniform -#elif defined(BC_HERMITE) && defined(BSPLINES_TYPE_UNIFORM) -#define SUFFIX(name) name##Hermite##Uniform -#elif defined(BC_HERMITE) && defined(BSPLINES_TYPE_NON_UNIFORM) -#define SUFFIX(name) name##Hermite##NonUniform +#if defined(BC_PERIODIC) && defined(BSPLINES_TYPE_UNIFORM) && defined(SOLVER_LAPACK) +#define SUFFIX(name) name##Lapack##Periodic##Uniform +#elif defined(BC_PERIODIC) && defined(BSPLINES_TYPE_NON_UNIFORM) && defined(SOLVER_LAPACK) +#define SUFFIX(name) name##Lapack##Periodic##NonUniform +#elif defined(BC_GREVILLE) && defined(BSPLINES_TYPE_UNIFORM) && defined(SOLVER_LAPACK) +#define SUFFIX(name) name##Lapack##Greville##Uniform +#elif defined(BC_GREVILLE) && defined(BSPLINES_TYPE_NON_UNIFORM) && defined(SOLVER_LAPACK) +#define SUFFIX(name) name##Lapack##Greville##NonUniform +#elif defined(BC_HERMITE) && defined(BSPLINES_TYPE_UNIFORM) && defined(SOLVER_LAPACK) +#define SUFFIX(name) name##Lapack##Hermite##Uniform +#elif defined(BC_HERMITE) && defined(BSPLINES_TYPE_NON_UNIFORM) && defined(SOLVER_LAPACK) +#define SUFFIX(name) name##Lapack##Hermite##NonUniform +#elif defined(BC_PERIODIC) && defined(BSPLINES_TYPE_NON_UNIFORM) && defined(SOLVER_GINKGO) +#define SUFFIX(name) name##Ginkgo##Periodic##Uniform +#elif defined(BC_PERIODIC) && defined(BSPLINES_TYPE_UNIFORM) && defined(SOLVER_GINKGO) +#define SUFFIX(name) name##Ginkgo##Periodic##NonUniform #endif TEST(SUFFIX(BatchedSplineHost), 1DX) From fdba50141d0c13a0ec52420d948c1d9244469f53 Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 5 Jun 2024 15:35:32 +0200 Subject: [PATCH 124/189] remove non-uniform guinkgo tst --- tests/splines/CMakeLists.txt | 2 +- tests/splines/batched_spline_builder.cpp | 2 -- 2 files changed, 1 insertion(+), 3 deletions(-) diff --git a/tests/splines/CMakeLists.txt b/tests/splines/CMakeLists.txt index ebc24f9b2..8327ec008 100644 --- a/tests/splines/CMakeLists.txt +++ b/tests/splines/CMakeLists.txt @@ -104,7 +104,7 @@ endforeach() # LAPACK foreach(BC "BC_PERIODIC" "BC_GREVILLE" "BC_HERMITE") foreach(DEGREE_X RANGE "${SPLINES_TEST_DEGREE_MIN}" "${SPLINES_TEST_DEGREE_MAX}") - foreach(BSPLINES_TYPE "BSPLINES_TYPE_UNIFORM" "BSPLINES_TYPE_NON_UNIFORM") + foreach(BSPLINES_TYPE "BSPLINES_TYPE_UNIFORM") set(test_name "splines_tests_BATCHED_DEGREE_X_${DEGREE_X}_${BSPLINES_TYPE}_${BC}_LAPACK") add_executable("${test_name}" ../main.cpp batched_spline_builder.cpp) target_compile_features("${test_name}" PUBLIC cxx_std_17) diff --git a/tests/splines/batched_spline_builder.cpp b/tests/splines/batched_spline_builder.cpp index 31c57f054..997e65872 100644 --- a/tests/splines/batched_spline_builder.cpp +++ b/tests/splines/batched_spline_builder.cpp @@ -434,8 +434,6 @@ static void BatchedSplineTest() #define SUFFIX(name) name##Lapack##Hermite##NonUniform #elif defined(BC_PERIODIC) && defined(BSPLINES_TYPE_NON_UNIFORM) && defined(SOLVER_GINKGO) #define SUFFIX(name) name##Ginkgo##Periodic##Uniform -#elif defined(BC_PERIODIC) && defined(BSPLINES_TYPE_UNIFORM) && defined(SOLVER_GINKGO) -#define SUFFIX(name) name##Ginkgo##Periodic##NonUniform #endif TEST(SUFFIX(BatchedSplineHost), 1DX) From 6bf1dee887e73162849ba01d09f60eb269a5ca54 Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 5 Jun 2024 15:36:42 +0200 Subject: [PATCH 125/189] typo --- tests/splines/CMakeLists.txt | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/tests/splines/CMakeLists.txt b/tests/splines/CMakeLists.txt index 8327ec008..f707a22f2 100644 --- a/tests/splines/CMakeLists.txt +++ b/tests/splines/CMakeLists.txt @@ -104,7 +104,7 @@ endforeach() # LAPACK foreach(BC "BC_PERIODIC" "BC_GREVILLE" "BC_HERMITE") foreach(DEGREE_X RANGE "${SPLINES_TEST_DEGREE_MIN}" "${SPLINES_TEST_DEGREE_MAX}") - foreach(BSPLINES_TYPE "BSPLINES_TYPE_UNIFORM") + foreach(BSPLINES_TYPE "BSPLINES_TYPE_UNIFORM" "BSPLINES_TYPE_NON_UNIFORM") set(test_name "splines_tests_BATCHED_DEGREE_X_${DEGREE_X}_${BSPLINES_TYPE}_${BC}_LAPACK") add_executable("${test_name}" ../main.cpp batched_spline_builder.cpp) target_compile_features("${test_name}" PUBLIC cxx_std_17) @@ -123,7 +123,7 @@ endforeach() # GINKGO foreach(BC "BC_PERIODIC") foreach(DEGREE_X RANGE "${SPLINES_TEST_DEGREE_MIN}" "${SPLINES_TEST_DEGREE_MAX}") - foreach(BSPLINES_TYPE "BSPLINES_TYPE_UNIFORM" "BSPLINES_TYPE_NON_UNIFORM") + foreach(BSPLINES_TYPE "BSPLINES_TYPE_UNIFORM") set(test_name "splines_tests_BATCHED_DEGREE_X_${DEGREE_X}_${BSPLINES_TYPE}_${BC}_GINKGO") add_executable("${test_name}" ../main.cpp batched_spline_builder.cpp) target_compile_features("${test_name}" PUBLIC cxx_std_17) From deeaedf46078283a4c1563fbde8199ace5b0d447 Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 5 Jun 2024 16:30:17 +0200 Subject: [PATCH 126/189] init + dense --- .gitmodules | 3 + CMakeLists.txt | 10 ++ .../splines/splines_linear_problem_dense.hpp | 121 ++++++++++++++---- vendor/kokkos-kernels | 1 + 4 files changed, 112 insertions(+), 23 deletions(-) create mode 160000 vendor/kokkos-kernels diff --git a/.gitmodules b/.gitmodules index a559a2afd..fd86ec400 100644 --- a/.gitmodules +++ b/.gitmodules @@ -15,3 +15,6 @@ [submodule "vendor/kokkos"] path = vendor/kokkos url = https://github.com/kokkos/kokkos.git +[submodule "vendor/kokkos-kernels"] + path = vendor/kokkos-kernels + url = git@github.com:kokkos/kokkos-kernels.git diff --git a/CMakeLists.txt b/CMakeLists.txt index c00a64135..7e2619487 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -253,6 +253,16 @@ if("${DDC_BUILD_KERNELS_SPLINES}") find_package(LAPACKE REQUIRED) target_link_libraries(DDC INTERFACE "${LAPACKE_LIBRARIES}") target_include_directories(DDC INTERFACE "${LAPACKE_INCLUDE_DIRS}") + + # Kokkos-kernels + set(KokkosKernels_ENABLE_ALL_COMPONENTS OFF) + set(KokkosKernels_ENABLE_COMPONENT_BLAS ON) + set(KokkosKernels_ENABLE_COMPONENT_BATCHED ON) + set(KokkosKernels_ENABLE_COMPONENT_LAPACK OFF) + set(KokkosKernels_ENABLE_TPL_BLAS ON) + set(KokkosKernels_ENABLE_TPL_LAPACK OFF) + add_subdirectory(vendor/kokkos-kernels/) + target_link_libraries(DDC INTERFACE Kokkos::kokkoskernels) endif() ## The PDI wrapper diff --git a/include/ddc/kernels/splines/splines_linear_problem_dense.hpp b/include/ddc/kernels/splines/splines_linear_problem_dense.hpp index e36f6e9b2..e98055ef8 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_dense.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_dense.hpp @@ -8,12 +8,17 @@ #include #include +#include + #if __has_include() #include #else #include #endif +#include +#include + #include "splines_linear_problem.hpp" namespace ddc::detail { @@ -33,8 +38,8 @@ class SplinesLinearProblemDense : public SplinesLinearProblem using SplinesLinearProblem::size; protected: - Kokkos::View m_a; - Kokkos::View m_ipiv; + Kokkos::DualView m_a; + Kokkos::DualView m_ipiv; public: /** @@ -47,21 +52,21 @@ class SplinesLinearProblemDense : public SplinesLinearProblem , m_a("a", mat_size, mat_size) , m_ipiv("ipiv", mat_size) { - Kokkos::deep_copy(m_a, 0.); + Kokkos::deep_copy(m_a.h_view, 0.); } double get_element(std::size_t const i, std::size_t const j) const override { assert(i < size()); assert(j < size()); - return m_a(i, j); + return m_a.h_view(i, j); } void set_element(std::size_t const i, std::size_t const j, double const aij) override { assert(i < size()); assert(j < size()); - m_a(i, j) = aij; + m_a.h_view(i, j) = aij; } /** @@ -75,13 +80,24 @@ class SplinesLinearProblemDense : public SplinesLinearProblem LAPACK_ROW_MAJOR, size(), size(), - m_a.data(), + m_a.h_view.data(), size(), - m_ipiv.data()); + m_ipiv.h_view.data()); if (info != 0) { throw std::runtime_error( "LAPACKE_dgetrf failed with error code " + std::to_string(info)); } + + // Adapt pivots to requirements of KokkosKernels::ApplyPivots + for (int i = 0; i < size(); ++i) { + m_ipiv.h_view(i) -= i + 1; + } + + // Push on device + m_a.modify_host(); + m_a.sync_device(); + m_ipiv.modify_host(); + m_ipiv.sync_device(); } /** @@ -96,23 +112,82 @@ class SplinesLinearProblemDense : public SplinesLinearProblem { assert(b.extent(0) == size()); - auto b_host = create_mirror_view(Kokkos::DefaultHostExecutionSpace(), b); - Kokkos::deep_copy(b_host, b); - int const info = LAPACKE_dgetrs( - LAPACK_ROW_MAJOR, - transpose ? 'T' : 'N', - b_host.extent(0), - b_host.extent(1), - m_a.data(), - b_host.extent(0), - m_ipiv.data(), - b_host.data(), - b_host.stride(0)); - if (info != 0) { - throw std::runtime_error( - "LAPACKE_dgetrs failed with error code " + std::to_string(info)); + auto a_device = m_a.d_view; + auto ipiv_device = m_ipiv.d_view; + + if (!transpose) { + Kokkos::parallel_for( + "gerts", + Kokkos::TeamPolicy(b.extent(1), Kokkos::AUTO), + KOKKOS_LAMBDA( + const typename Kokkos::TeamPolicy::member_type& teamMember) { + const int i = teamMember.league_rank(); + + auto b_slice = Kokkos::subview(b, Kokkos::ALL, i); + + teamMember.team_barrier(); + KokkosBatched::TeamVectorApplyPivot< + typename Kokkos::TeamPolicy::member_type, + KokkosBatched::Side::Left, + KokkosBatched::Direct::Forward>:: + invoke(teamMember, ipiv_device, b_slice); + teamMember.team_barrier(); + KokkosBatched::TeamVectorTrsm< + typename Kokkos::TeamPolicy::member_type, + KokkosBatched::Side::Left, + KokkosBatched::Uplo::Lower, + KokkosBatched::Trans::NoTranspose, + KokkosBatched::Diag::Unit, + KokkosBatched::Algo::Level3::Unblocked>:: + invoke(teamMember, 1.0, a_device, b_slice); + teamMember.team_barrier(); + KokkosBatched::TeamVectorTrsm< + typename Kokkos::TeamPolicy::member_type, + KokkosBatched::Side::Left, + KokkosBatched::Uplo::Upper, + KokkosBatched::Trans::NoTranspose, + KokkosBatched::Diag::NonUnit, + KokkosBatched::Algo::Level3::Unblocked>:: + invoke(teamMember, 1.0, a_device, b_slice); + teamMember.team_barrier(); + }); + } else { + Kokkos::parallel_for( + "gerts_tr", + Kokkos::TeamPolicy(b.extent(1), Kokkos::AUTO), + KOKKOS_LAMBDA( + const typename Kokkos::TeamPolicy::member_type& teamMember) { + const int i = teamMember.league_rank(); + + auto b_slice = Kokkos::subview(b, Kokkos::ALL, i); + + teamMember.team_barrier(); + KokkosBatched::TeamVectorTrsm< + typename Kokkos::TeamPolicy::member_type, + KokkosBatched::Side::Left, + KokkosBatched::Uplo::Upper, + KokkosBatched::Trans::Transpose, + KokkosBatched::Diag::NonUnit, + KokkosBatched::Algo::Level3::Unblocked>:: + invoke(teamMember, 1.0, a_device, b_slice); + teamMember.team_barrier(); + KokkosBatched::TeamVectorTrsm< + typename Kokkos::TeamPolicy::member_type, + KokkosBatched::Side::Left, + KokkosBatched::Uplo::Lower, + KokkosBatched::Trans::Transpose, + KokkosBatched::Diag::Unit, + KokkosBatched::Algo::Level3::Unblocked>:: + invoke(teamMember, 1.0, a_device, b_slice); + teamMember.team_barrier(); + KokkosBatched::TeamVectorApplyPivot< + typename Kokkos::TeamPolicy::member_type, + KokkosBatched::Side::Left, + KokkosBatched::Direct::Backward>:: + invoke(teamMember, ipiv_device, b_slice); + teamMember.team_barrier(); + }); } - Kokkos::deep_copy(b, b_host); } }; diff --git a/vendor/kokkos-kernels b/vendor/kokkos-kernels new file mode 160000 index 000000000..f429f6ecb --- /dev/null +++ b/vendor/kokkos-kernels @@ -0,0 +1 @@ +Subproject commit f429f6ecbd73b977c37573f00004228075754129 From c018ad568dd1206b6cf0c9a3c165b56c02d2a2da Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 5 Jun 2024 16:34:04 +0200 Subject: [PATCH 127/189] typo --- tests/splines/batched_spline_builder.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/splines/batched_spline_builder.cpp b/tests/splines/batched_spline_builder.cpp index 997e65872..c2d57805e 100644 --- a/tests/splines/batched_spline_builder.cpp +++ b/tests/splines/batched_spline_builder.cpp @@ -432,7 +432,7 @@ static void BatchedSplineTest() #define SUFFIX(name) name##Lapack##Hermite##Uniform #elif defined(BC_HERMITE) && defined(BSPLINES_TYPE_NON_UNIFORM) && defined(SOLVER_LAPACK) #define SUFFIX(name) name##Lapack##Hermite##NonUniform -#elif defined(BC_PERIODIC) && defined(BSPLINES_TYPE_NON_UNIFORM) && defined(SOLVER_GINKGO) +#elif defined(BC_PERIODIC) && defined(BSPLINES_TYPE_UNIFORM) && defined(SOLVER_GINKGO) #define SUFFIX(name) name##Ginkgo##Periodic##Uniform #endif From bef12fd9ee529d58102311d3a94598d09c6d8d71 Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 5 Jun 2024 17:08:28 +0200 Subject: [PATCH 128/189] pdsband --- .../splines_linear_problem_pds_band.hpp | 100 +++++++++++++----- 1 file changed, 75 insertions(+), 25 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp b/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp index 052429d34..55f7507a0 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp @@ -39,7 +39,8 @@ class SplinesLinearProblemPDSBand : public SplinesLinearProblem using SplinesLinearProblem::size; protected: - Kokkos::View m_q; // pds band matrix representation + Kokkos::DualView + m_q; // pds band matrix representation public: /** @@ -54,7 +55,7 @@ class SplinesLinearProblemPDSBand : public SplinesLinearProblem { assert(m_q.extent(0) <= mat_size); - Kokkos::deep_copy(m_q, 0.); + Kokkos::deep_copy(m_q.h_view, 0.); } double get_element(std::size_t i, std::size_t j) const override @@ -67,7 +68,7 @@ class SplinesLinearProblemPDSBand : public SplinesLinearProblem std::swap(i, j); } if (j - i < m_q.extent(0)) { - return m_q(j - i, i); + return m_q.h_view(j - i, i); } else { return 0.0; } @@ -83,7 +84,7 @@ class SplinesLinearProblemPDSBand : public SplinesLinearProblem std::swap(i, j); } if (j - i < m_q.extent(0)) { - m_q(j - i, i) = aij; + m_q.h_view(j - i, i) = aij; } else { assert(std::fabs(aij) < 1e-20); } @@ -101,16 +102,53 @@ class SplinesLinearProblemPDSBand : public SplinesLinearProblem 'L', size(), m_q.extent(0) - 1, - m_q.data(), - m_q.stride( - 0) // m_q.stride(0) if LAPACK_ROW_MAJOR, m_q.stride(1) if LAPACK_COL_MAJOR + m_q.h_view.data(), + m_q.h_view.stride( + 0) // m_q.h_view.stride(0) if LAPACK_ROW_MAJOR, m_q.h_view.stride(1) if LAPACK_COL_MAJOR ); if (info != 0) { throw std::runtime_error( "LAPACKE_dpbtrf failed with error code " + std::to_string(info)); } + + // Push on device + m_q.modify_host(); + m_q.sync_device(); + } + +private: + KOKKOS_FUNCTION int tbsv( + char const uplo, + char const trans, + char const diag, + int const n, + int const k, + Kokkos::View const a, + int const lda, + Kokkos::View const x, + int const incx) const + { + if (trans == 'N') { + for (int j = 0; j < n; ++j) { + if (x(j) != 0) { + x(j) /= a(0, j); + for (int i = j + 1; i <= Kokkos::min(n, j + k); ++i) { + x(i) -= a(i - j, j) * x(j); + } + } + } + } else if (trans == 'T') { + for (int j = n - 1; j >= 0; --j) { + for (int i = Kokkos::min(n, j + k); i >= j + 1; --i) { + x(j) -= a(i - j, j) * x(i); + } + x(j) /= a(0, j); + } + } + return 0; } +public: /** * @brief Solve the multiple right-hand sides linear problem Ax=b or its transposed version A^tx=b inplace. * @@ -123,24 +161,36 @@ class SplinesLinearProblemPDSBand : public SplinesLinearProblem { assert(b.extent(0) == size()); - auto b_host = create_mirror_view(Kokkos::DefaultHostExecutionSpace(), b); - Kokkos::deep_copy(b_host, b); - int const info = LAPACKE_dpbtrs( - LAPACK_ROW_MAJOR, - 'L', - b_host.extent(0), - m_q.extent(0) - 1, - b_host.extent(1), - m_q.data(), - m_q.stride( - 0), // m_q.stride(0) if LAPACK_ROW_MAJOR, m_q.stride(1) if LAPACK_COL_MAJOR - b_host.data(), - b_host.stride(0)); - if (info != 0) { - throw std::runtime_error( - "LAPACKE_dpbtrs failed with error code " + std::to_string(info)); - } - Kokkos::deep_copy(b, b_host); + auto q_device = m_q.d_view; + + Kokkos::parallel_for( + "pbtrs", + Kokkos::RangePolicy(0, b.extent(1)), + KOKKOS_CLASS_LAMBDA(const int i) { + auto b_slice = Kokkos::subview(b, Kokkos::ALL, i); + + int info; + info + = tbsv('L', + 'N', + 'N', + q_device.extent(1), + q_device.extent(0) - 1, + q_device, + q_device.extent(0) - 1, + b_slice, + 1); + info + = tbsv('L', + 'T', + 'N', + q_device.extent(1), + q_device.extent(0) - 1, + q_device, + q_device.extent(0) - 1, + b_slice, + 1); + }); } }; From 5a1df3aae11353de9c12206df3e9ec8e34b46255 Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 5 Jun 2024 17:39:02 +0200 Subject: [PATCH 129/189] pdstridiag --- .../splines/splines_linear_problem_dense.hpp | 2 +- .../splines_linear_problem_pds_band.hpp | 2 + .../splines_linear_problem_pds_tridiag.hpp | 51 +++++++++++-------- 3 files changed, 34 insertions(+), 21 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_dense.hpp b/include/ddc/kernels/splines/splines_linear_problem_dense.hpp index e98055ef8..bfc5fa7cd 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_dense.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_dense.hpp @@ -17,7 +17,7 @@ #endif #include -#include +#include #include "splines_linear_problem.hpp" diff --git a/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp b/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp index 55f7507a0..ffdcbb3d5 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp @@ -8,6 +8,8 @@ #include #include +#include + #if __has_include() #include #else diff --git a/include/ddc/kernels/splines/splines_linear_problem_pds_tridiag.hpp b/include/ddc/kernels/splines/splines_linear_problem_pds_tridiag.hpp index c7067958c..bbbd57f21 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_pds_tridiag.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_pds_tridiag.hpp @@ -8,6 +8,8 @@ #include #include +#include + #if __has_include() #include #else @@ -39,7 +41,8 @@ class SplinesLinearProblemPDSTridiag : public SplinesLinearProblem using SplinesLinearProblem::size; protected: - Kokkos::View m_q; // pds band matrix representation + Kokkos::DualView + m_q; // pds tridiagonal matrix representation public: /** @@ -51,7 +54,7 @@ class SplinesLinearProblemPDSTridiag : public SplinesLinearProblem : SplinesLinearProblem(mat_size) , m_q("q", 2, mat_size) { - Kokkos::deep_copy(m_q, 0.); + Kokkos::deep_copy(m_q.h_view, 0.); } double get_element(std::size_t i, std::size_t j) const override @@ -64,7 +67,7 @@ class SplinesLinearProblemPDSTridiag : public SplinesLinearProblem std::swap(i, j); } if (j - i < 2) { - return m_q(j - i, i); + return m_q.h_view(j - i, i); } else { return 0.0; } @@ -80,7 +83,7 @@ class SplinesLinearProblemPDSTridiag : public SplinesLinearProblem std::swap(i, j); } if (j - i < 2) { - m_q(j - i, i) = aij; + m_q.h_view(j - i, i) = aij; } else { assert(std::fabs(aij) < 1e-20); } @@ -93,11 +96,18 @@ class SplinesLinearProblemPDSTridiag : public SplinesLinearProblem */ void setup_solver() override { - int const info = LAPACKE_dpttrf(size(), m_q.data(), m_q.data() + m_q.stride(0)); + int const info = LAPACKE_dpttrf( + size(), + m_q.h_view.data(), + m_q.h_view.data() + m_q.h_view.stride(0)); if (info != 0) { throw std::runtime_error( "LAPACKE_dpttrf failed with error code " + std::to_string(info)); } + + // Push on device + m_q.modify_host(); + m_q.sync_device(); } /** @@ -112,21 +122,22 @@ class SplinesLinearProblemPDSTridiag : public SplinesLinearProblem { assert(b.extent(0) == size()); - auto b_host = create_mirror_view(Kokkos::DefaultHostExecutionSpace(), b); - Kokkos::deep_copy(b_host, b); - int const info = LAPACKE_dpttrs( - LAPACK_ROW_MAJOR, - b_host.extent(0), - b_host.extent(1), - m_q.data(), - m_q.data() + m_q.stride(0), - b_host.data(), - b_host.stride(0)); - if (info != 0) { - throw std::runtime_error( - "LAPACKE_dpttrs failed with error code " + std::to_string(info)); - } - Kokkos::deep_copy(b, b_host); + auto q_device = m_q.d_view; + + Kokkos::parallel_for( + "pttrs", + Kokkos::RangePolicy(0, b.extent(1)), + KOKKOS_LAMBDA(const int i) { + auto b_slice = Kokkos::subview(b, Kokkos::ALL, i); + + for (int j = 1; j < q_device.extent(1); ++j) { + b_slice(j) -= b_slice(j - 1) * q_device(1, j - 1); + } + b_slice(q_device.extent(1) - 1) /= q_device(0, q_device.extent(1) - 1); + for (int j = q_device.extent(1) - 2; j >= 0; --j) { + b_slice(j) = b_slice(j) / q_device(0, j) - b_slice(j + 1) * q_device(1, j); + } + }); } }; From a1713b83eb2fea33342e582b8c9514a43b320050 Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 5 Jun 2024 18:39:11 +0200 Subject: [PATCH 130/189] wip on gemv (not working) --- .../splines_linear_problem_2x2_blocks.hpp | 44 ++++++++----------- 1 file changed, 19 insertions(+), 25 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp index fe605d71d..246f0a491 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp @@ -10,6 +10,8 @@ #include +#include + #include "splines_linear_problem.hpp" #include "splines_linear_problem_dense.hpp" @@ -192,19 +194,15 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem Kokkos::TeamPolicy(y.extent(0) * y.extent(1), Kokkos::AUTO), KOKKOS_LAMBDA( const typename Kokkos::TeamPolicy::member_type& teamMember) { - const int i = teamMember.league_rank() / y.extent(1); - const int j = teamMember.league_rank() % y.extent(1); + const int i = teamMember.league_rank(); + + auto x_slice = Kokkos::subview(x, Kokkos::ALL, i); + auto y_slice = Kokkos::subview(y, Kokkos::ALL, i); - double LinOpTimesX = 0.; - Kokkos::parallel_reduce( - Kokkos::TeamThreadRange(teamMember, x.extent(0)), - [&](const int l, double& LinOpTimesX_tmp) { - LinOpTimesX_tmp += LinOp(i, l) * x(l, j); - }, - LinOpTimesX); - Kokkos::single(Kokkos::PerTeam(teamMember), [&]() { - y(i, j) -= LinOpTimesX; - }); + teamMember.team_barrier(); + KokkosBlas::Experimental::team_gemv + (teamMember, 'N', -1, LinOp, x_slice, 1, y_slice); + teamMember.team_barrier(); }); } else { Kokkos::parallel_for( @@ -212,20 +210,16 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem Kokkos::TeamPolicy(y.extent(0) * y.extent(1), Kokkos::AUTO), KOKKOS_LAMBDA( const typename Kokkos::TeamPolicy::member_type& teamMember) { - const int i = teamMember.league_rank() / y.extent(1); - const int j = teamMember.league_rank() % y.extent(1); + const int i = teamMember.league_rank(); - double LinOpTimesX = 0.; - Kokkos::parallel_reduce( - Kokkos::TeamThreadRange(teamMember, x.extent(0)), - [&](const int l, double& LinOpTimesX_tmp) { - LinOpTimesX_tmp += LinOp(l, i) * x(l, j); - }, - LinOpTimesX); - Kokkos::single(Kokkos::PerTeam(teamMember), [&]() { - y(i, j) -= LinOpTimesX; - }); - }); + auto x_slice = Kokkos::subview(x, Kokkos::ALL, i); + auto y_slice = Kokkos::subview(y, Kokkos::ALL, i); + + teamMember.team_barrier(); + KokkosBlas::Experimental::team_gemv + (teamMember, 'T', -1, LinOp, x_slice, 1, y_slice); + teamMember.team_barrier(); + }); } } From 9b5af1d7485065431f224846d2ea428a3ef5f777 Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 5 Jun 2024 19:16:17 +0200 Subject: [PATCH 131/189] wip --- .../splines_linear_problem_2x2_blocks.hpp | 16 ++++++++++++---- 1 file changed, 12 insertions(+), 4 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp index 246f0a491..8ed8b1fa9 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp @@ -11,6 +11,7 @@ #include #include +#include #include "splines_linear_problem.hpp" #include "splines_linear_problem_dense.hpp" @@ -245,6 +246,9 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem { assert(b.extent(0) == size()); + auto bottom_left_block = m_bottom_left_block.d_view; + auto top_right_block = m_top_right_block.d_view; + MultiRHS b1 = Kokkos:: subview(b, std::pair(0, m_top_left_block->size()), @@ -255,13 +259,17 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem Kokkos::ALL); if (!transpose) { m_top_left_block->solve(b1); - gemv_minus1_1(b1, b2, m_bottom_left_block.d_view); + // gemv_minus1_1(b1, b2, m_bottom_left_block.d_view); + KokkosBlas::gemm(ExecSpace(), "N", "N", -1., bottom_left_block, b1, 1., b2); m_bottom_right_block->solve(b2); - gemv_minus1_1(b2, b1, m_top_right_block.d_view); + // gemv_minus1_1(b2, b1, m_top_right_block.d_view); + KokkosBlas::gemm(ExecSpace(), "N", "N", -1., top_right_block, b2, 1., b1); } else { - gemv_minus1_1(b1, b2, m_top_right_block.d_view, true); + // gemv_minus1_1(b1, b2, m_top_right_block.d_view, true); + KokkosBlas::gemm(ExecSpace(), "T", "N", -1., top_right_block, b1, 1., b2); m_bottom_right_block->solve(b2, true); - gemv_minus1_1(b2, b1, m_bottom_left_block.d_view, true); + // gemv_minus1_1(b2, b1, m_bottom_left_block.d_view, true); + KokkosBlas::gemm(ExecSpace(), "T", "N", -1., bottom_left_block, b2, 1., b1); m_top_left_block->solve(b1, true); } } From 0df293127f827b4ad0457f4d654506cc523e2397 Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 5 Jun 2024 19:20:21 +0200 Subject: [PATCH 132/189] KokkosBlas::gemm --- .../splines_linear_problem_2x2_blocks.hpp | 77 ++----------------- 1 file changed, 5 insertions(+), 72 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp index 8ed8b1fa9..35d8c1e99 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp @@ -8,10 +8,8 @@ #include #include -#include - -#include #include +#include #include "splines_linear_problem.hpp" #include "splines_linear_problem_dense.hpp" @@ -166,64 +164,6 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem m_bottom_right_block->setup_solver(); } - /** - * @brief Compute y <- y - LinOp*x or y <- y - LinOp^t*x. - * - * [SHOULD BE PRIVATE (GPU programming limitation)] - * - * @param x - * @param y - * @param LinOp - * @param transpose - */ - void gemv_minus1_1( - MultiRHS const x, - MultiRHS const y, - Kokkos::View const - LinOp, - bool const transpose = false) const - { - assert((!transpose && LinOp.extent(0) == y.extent(0)) - || (transpose && LinOp.extent(1) == y.extent(0))); - assert((!transpose && LinOp.extent(1) == x.extent(0)) - || (transpose && LinOp.extent(0) == x.extent(0))); - assert(x.extent(1) == y.extent(1)); - - if (!transpose) { - Kokkos::parallel_for( - "gemv_minus1_1", - Kokkos::TeamPolicy(y.extent(0) * y.extent(1), Kokkos::AUTO), - KOKKOS_LAMBDA( - const typename Kokkos::TeamPolicy::member_type& teamMember) { - const int i = teamMember.league_rank(); - - auto x_slice = Kokkos::subview(x, Kokkos::ALL, i); - auto y_slice = Kokkos::subview(y, Kokkos::ALL, i); - - teamMember.team_barrier(); - KokkosBlas::Experimental::team_gemv - (teamMember, 'N', -1, LinOp, x_slice, 1, y_slice); - teamMember.team_barrier(); - }); - } else { - Kokkos::parallel_for( - "gemv_minus1_1_tr", - Kokkos::TeamPolicy(y.extent(0) * y.extent(1), Kokkos::AUTO), - KOKKOS_LAMBDA( - const typename Kokkos::TeamPolicy::member_type& teamMember) { - const int i = teamMember.league_rank(); - - auto x_slice = Kokkos::subview(x, Kokkos::ALL, i); - auto y_slice = Kokkos::subview(y, Kokkos::ALL, i); - - teamMember.team_barrier(); - KokkosBlas::Experimental::team_gemv - (teamMember, 'T', -1, LinOp, x_slice, 1, y_slice); - teamMember.team_barrier(); - }); - } - } - /** * @brief Solve the multiple right-hand sides linear problem Ax=b or its transposed version A^tx=b inplace. * @@ -246,9 +186,6 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem { assert(b.extent(0) == size()); - auto bottom_left_block = m_bottom_left_block.d_view; - auto top_right_block = m_top_right_block.d_view; - MultiRHS b1 = Kokkos:: subview(b, std::pair(0, m_top_left_block->size()), @@ -259,17 +196,13 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem Kokkos::ALL); if (!transpose) { m_top_left_block->solve(b1); - // gemv_minus1_1(b1, b2, m_bottom_left_block.d_view); - KokkosBlas::gemm(ExecSpace(), "N", "N", -1., bottom_left_block, b1, 1., b2); + KokkosBlas::gemm(ExecSpace(), "N", "N", -1., m_bottom_left_block.d_view, b1, 1., b2); m_bottom_right_block->solve(b2); - // gemv_minus1_1(b2, b1, m_top_right_block.d_view); - KokkosBlas::gemm(ExecSpace(), "N", "N", -1., top_right_block, b2, 1., b1); + KokkosBlas::gemm(ExecSpace(), "N", "N", -1., m_top_right_block.d_view, b2, 1., b1); } else { - // gemv_minus1_1(b1, b2, m_top_right_block.d_view, true); - KokkosBlas::gemm(ExecSpace(), "T", "N", -1., top_right_block, b1, 1., b2); + KokkosBlas::gemm(ExecSpace(), "T", "N", -1., m_top_right_block.d_view, b1, 1., b2); m_bottom_right_block->solve(b2, true); - // gemv_minus1_1(b2, b1, m_bottom_left_block.d_view, true); - KokkosBlas::gemm(ExecSpace(), "T", "N", -1., bottom_left_block, b2, 1., b1); + KokkosBlas::gemm(ExecSpace(), "T", "N", -1., m_bottom_left_block.d_view, b2, 1., b1); m_top_left_block->solve(b1, true); } } From e9b6287c2221ab318be53b6ab5889be671d9b961 Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 5 Jun 2024 19:49:32 +0200 Subject: [PATCH 133/189] LAPACK backend as defaut for example & benchmark --- benchmarks/splines.cpp | 2 +- examples/characteristics_advection.cpp | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/benchmarks/splines.cpp b/benchmarks/splines.cpp index f6bda61f0..6902b6e08 100644 --- a/benchmarks/splines.cpp +++ b/benchmarks/splines.cpp @@ -117,7 +117,7 @@ static void characteristics_advection(benchmark::State& state) DDimX, ddc::BoundCond::PERIODIC, ddc::BoundCond::PERIODIC, - ddc::SplineSolver::GINKGO, + ddc::SplineSolver::LAPACK, DDimX, DDimY> spline_builder(x_mesh, state.range(2), state.range(3)); diff --git a/examples/characteristics_advection.cpp b/examples/characteristics_advection.cpp index 77ad725fc..133c2b2e5 100644 --- a/examples/characteristics_advection.cpp +++ b/examples/characteristics_advection.cpp @@ -217,7 +217,7 @@ int main(int argc, char** argv) DDimX, ddc::BoundCond::PERIODIC, ddc::BoundCond::PERIODIC, - ddc::SplineSolver::GINKGO, + ddc::SplineSolver::LAPACK, DDimX, DDimY> spline_builder(x_mesh); From 5ca14c263e1e86f3363b4a6754d54a6dbbd33528 Mon Sep 17 00:00:00 2001 From: blegouix Date: Thu, 6 Jun 2024 12:49:21 +0200 Subject: [PATCH 134/189] minor --- .../splines/splines_linear_problem_pds_band.hpp | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp b/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp index ffdcbb3d5..d86e8333a 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp @@ -120,15 +120,15 @@ class SplinesLinearProblemPDSBand : public SplinesLinearProblem private: KOKKOS_FUNCTION int tbsv( - char const uplo, - char const trans, - char const diag, + [[maybe_unused]] char const uplo, + [[maybe_unused]] char const trans, + [[maybe_unused]] char const diag, int const n, int const k, Kokkos::View const a, - int const lda, + [[maybe_unused]] int const lda, Kokkos::View const x, - int const incx) const + [[maybe_unused]] int const incx) const { if (trans == 'N') { for (int j = 0; j < n; ++j) { @@ -179,7 +179,7 @@ class SplinesLinearProblemPDSBand : public SplinesLinearProblem q_device.extent(1), q_device.extent(0) - 1, q_device, - q_device.extent(0) - 1, + q_device.extent(0), b_slice, 1); info @@ -189,7 +189,7 @@ class SplinesLinearProblemPDSBand : public SplinesLinearProblem q_device.extent(1), q_device.extent(0) - 1, q_device, - q_device.extent(0) - 1, + q_device.extent(0), b_slice, 1); }); From 93919d4e0292bb3abeb13ac4d0a148423a7cd41c Mon Sep 17 00:00:00 2001 From: Yuuichi Asahi Date: Tue, 11 Jun 2024 09:13:01 +0200 Subject: [PATCH 135/189] testing KK backend --- .gitmodules | 3 + CMakeLists.txt | 10 +++ benchmarks/splines.cpp | 2 +- examples/characteristics_advection.cpp | 2 +- .../splines_linear_problem_2x2_blocks.hpp | 77 ++----------------- .../splines/splines_linear_problem_dense.hpp | 73 ++++++++++++------ .../splines/splines_linear_problem_maker.hpp | 56 ++++++++++++-- .../splines_linear_problem_pds_band.hpp | 53 +++++++------ .../splines_linear_problem_pds_tridiag.hpp | 49 +++++++----- vendor/benchmark | 2 +- vendor/kokkos-kernels | 1 + 11 files changed, 177 insertions(+), 151 deletions(-) create mode 160000 vendor/kokkos-kernels diff --git a/.gitmodules b/.gitmodules index a559a2afd..f4d5668ec 100644 --- a/.gitmodules +++ b/.gitmodules @@ -15,3 +15,6 @@ [submodule "vendor/kokkos"] path = vendor/kokkos url = https://github.com/kokkos/kokkos.git +[submodule "vendor/kokkos-kernels"] + path = vendor/kokkos-kernels + url = https://github.com/yasahi-hpc/kokkos-kernels.git diff --git a/CMakeLists.txt b/CMakeLists.txt index c00a64135..7e2619487 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -253,6 +253,16 @@ if("${DDC_BUILD_KERNELS_SPLINES}") find_package(LAPACKE REQUIRED) target_link_libraries(DDC INTERFACE "${LAPACKE_LIBRARIES}") target_include_directories(DDC INTERFACE "${LAPACKE_INCLUDE_DIRS}") + + # Kokkos-kernels + set(KokkosKernels_ENABLE_ALL_COMPONENTS OFF) + set(KokkosKernels_ENABLE_COMPONENT_BLAS ON) + set(KokkosKernels_ENABLE_COMPONENT_BATCHED ON) + set(KokkosKernels_ENABLE_COMPONENT_LAPACK OFF) + set(KokkosKernels_ENABLE_TPL_BLAS ON) + set(KokkosKernels_ENABLE_TPL_LAPACK OFF) + add_subdirectory(vendor/kokkos-kernels/) + target_link_libraries(DDC INTERFACE Kokkos::kokkoskernels) endif() ## The PDI wrapper diff --git a/benchmarks/splines.cpp b/benchmarks/splines.cpp index f6bda61f0..6902b6e08 100644 --- a/benchmarks/splines.cpp +++ b/benchmarks/splines.cpp @@ -117,7 +117,7 @@ static void characteristics_advection(benchmark::State& state) DDimX, ddc::BoundCond::PERIODIC, ddc::BoundCond::PERIODIC, - ddc::SplineSolver::GINKGO, + ddc::SplineSolver::LAPACK, DDimX, DDimY> spline_builder(x_mesh, state.range(2), state.range(3)); diff --git a/examples/characteristics_advection.cpp b/examples/characteristics_advection.cpp index 77ad725fc..133c2b2e5 100644 --- a/examples/characteristics_advection.cpp +++ b/examples/characteristics_advection.cpp @@ -217,7 +217,7 @@ int main(int argc, char** argv) DDimX, ddc::BoundCond::PERIODIC, ddc::BoundCond::PERIODIC, - ddc::SplineSolver::GINKGO, + ddc::SplineSolver::LAPACK, DDimX, DDimY> spline_builder(x_mesh); diff --git a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp index c459166fb..35d8c1e99 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp @@ -8,6 +8,7 @@ #include #include +#include #include #include "splines_linear_problem.hpp" @@ -50,7 +51,7 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem * @brief SplinesLinearProblem2x2Blocks constructor. * * @param mat_size The size of one of the dimensions of the square matrix. - * @param top_left_block A pointer toward the top-left SplinesLinearProblem. `setup_solver` must not have been called on `q`. + * @param top_left_block A pointer toward the top-left SplinesLinearProblem. `setup_solver` must not have been called on it. */ explicit SplinesLinearProblem2x2Blocks( std::size_t const mat_size, @@ -163,72 +164,6 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem m_bottom_right_block->setup_solver(); } - /** - * @brief Compute y <- y - LinOp*x or y <- y - LinOp^t*x. - * - * [SHOULD BE PRIVATE (GPU programming limitation)] - * - * @param x - * @param y - * @param LinOp - * @param transpose - */ - void gemv_minus1_1( - MultiRHS const x, - MultiRHS const y, - Kokkos::View const - LinOp, - bool const transpose = false) const - { - assert((!transpose && LinOp.extent(0) == y.extent(0)) - || (transpose && LinOp.extent(1) == y.extent(0))); - assert((!transpose && LinOp.extent(1) == x.extent(0)) - || (transpose && LinOp.extent(0) == x.extent(0))); - assert(x.extent(1) == y.extent(1)); - - if (!transpose) { - Kokkos::parallel_for( - "gemv_minus1_1", - Kokkos::TeamPolicy(y.extent(0) * y.extent(1), Kokkos::AUTO), - KOKKOS_LAMBDA( - const typename Kokkos::TeamPolicy::member_type& teamMember) { - const int i = teamMember.league_rank() / y.extent(1); - const int j = teamMember.league_rank() % y.extent(1); - - double LinOpTimesX = 0.; - Kokkos::parallel_reduce( - Kokkos::TeamThreadRange(teamMember, x.extent(0)), - [&](const int l, double& LinOpTimesX_tmp) { - LinOpTimesX_tmp += LinOp(i, l) * x(l, j); - }, - LinOpTimesX); - Kokkos::single(Kokkos::PerTeam(teamMember), [&]() { - y(i, j) -= LinOpTimesX; - }); - }); - } else { - Kokkos::parallel_for( - "gemv_minus1_1_tr", - Kokkos::TeamPolicy(y.extent(0) * y.extent(1), Kokkos::AUTO), - KOKKOS_LAMBDA( - const typename Kokkos::TeamPolicy::member_type& teamMember) { - const int i = teamMember.league_rank() / y.extent(1); - const int j = teamMember.league_rank() % y.extent(1); - - double LinOpTimesX = 0.; - Kokkos::parallel_reduce( - Kokkos::TeamThreadRange(teamMember, x.extent(0)), - [&](const int l, double& LinOpTimesX_tmp) { - LinOpTimesX_tmp += LinOp(l, i) * x(l, j); - }, - LinOpTimesX); - Kokkos::single(Kokkos::PerTeam(teamMember), [&]() { - y(i, j) -= LinOpTimesX; - }); - }); - } - } - /** * @brief Solve the multiple right-hand sides linear problem Ax=b or its transposed version A^tx=b inplace. * @@ -261,13 +196,13 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem Kokkos::ALL); if (!transpose) { m_top_left_block->solve(b1); - gemv_minus1_1(b1, b2, m_bottom_left_block.d_view); + KokkosBlas::gemm(ExecSpace(), "N", "N", -1., m_bottom_left_block.d_view, b1, 1., b2); m_bottom_right_block->solve(b2); - gemv_minus1_1(b2, b1, m_top_right_block.d_view); + KokkosBlas::gemm(ExecSpace(), "N", "N", -1., m_top_right_block.d_view, b2, 1., b1); } else { - gemv_minus1_1(b1, b2, m_top_right_block.d_view, true); + KokkosBlas::gemm(ExecSpace(), "T", "N", -1., m_top_right_block.d_view, b1, 1., b2); m_bottom_right_block->solve(b2, true); - gemv_minus1_1(b2, b1, m_bottom_left_block.d_view, true); + KokkosBlas::gemm(ExecSpace(), "T", "N", -1., m_bottom_left_block.d_view, b2, 1., b1); m_top_left_block->solve(b1, true); } } diff --git a/include/ddc/kernels/splines/splines_linear_problem_dense.hpp b/include/ddc/kernels/splines/splines_linear_problem_dense.hpp index e36f6e9b2..504b45c2c 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_dense.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_dense.hpp @@ -8,12 +8,17 @@ #include #include +#include + #if __has_include() #include #else #include #endif +#include +#include + #include "splines_linear_problem.hpp" namespace ddc::detail { @@ -33,8 +38,8 @@ class SplinesLinearProblemDense : public SplinesLinearProblem using SplinesLinearProblem::size; protected: - Kokkos::View m_a; - Kokkos::View m_ipiv; + Kokkos::DualView m_a; + Kokkos::DualView m_ipiv; public: /** @@ -47,21 +52,21 @@ class SplinesLinearProblemDense : public SplinesLinearProblem , m_a("a", mat_size, mat_size) , m_ipiv("ipiv", mat_size) { - Kokkos::deep_copy(m_a, 0.); + Kokkos::deep_copy(m_a.h_view, 0.); } double get_element(std::size_t const i, std::size_t const j) const override { assert(i < size()); assert(j < size()); - return m_a(i, j); + return m_a.h_view(i, j); } void set_element(std::size_t const i, std::size_t const j, double const aij) override { assert(i < size()); assert(j < size()); - m_a(i, j) = aij; + m_a.h_view(i, j) = aij; } /** @@ -75,13 +80,24 @@ class SplinesLinearProblemDense : public SplinesLinearProblem LAPACK_ROW_MAJOR, size(), size(), - m_a.data(), + m_a.h_view.data(), size(), - m_ipiv.data()); + m_ipiv.h_view.data()); if (info != 0) { throw std::runtime_error( "LAPACKE_dgetrf failed with error code " + std::to_string(info)); } + + // Convert 1-based index to 0-based index + for (int i = 0; i < size(); ++i) { + m_ipiv.h_view(i) -= 1; + } + + // Push on device + m_a.modify_host(); + m_a.sync_device(); + m_ipiv.modify_host(); + m_ipiv.sync_device(); } /** @@ -96,23 +112,34 @@ class SplinesLinearProblemDense : public SplinesLinearProblem { assert(b.extent(0) == size()); - auto b_host = create_mirror_view(Kokkos::DefaultHostExecutionSpace(), b); - Kokkos::deep_copy(b_host, b); - int const info = LAPACKE_dgetrs( - LAPACK_ROW_MAJOR, - transpose ? 'T' : 'N', - b_host.extent(0), - b_host.extent(1), - m_a.data(), - b_host.extent(0), - m_ipiv.data(), - b_host.data(), - b_host.stride(0)); - if (info != 0) { - throw std::runtime_error( - "LAPACKE_dgetrs failed with error code " + std::to_string(info)); + auto a_device = m_a.d_view; + auto ipiv_device = m_ipiv.d_view; + + Kokkos::RangePolicy policy(0, b.extent(1)); + + if (transpose) { + Kokkos::parallel_for( + "gerts", + policy, + KOKKOS_LAMBDA(const int i) { + auto sub_b = Kokkos::subview(b, Kokkos::ALL, i); + KokkosBatched::SerialGetrs< + KokkosBatched::Trans::Transpose, + KokkosBatched::Algo::Getrs::Unblocked>:: + invoke(a_device, ipiv_device, sub_b); + }); + } else { + Kokkos::parallel_for( + "gerts", + policy, + KOKKOS_LAMBDA(const int i) { + auto sub_b = Kokkos::subview(b, Kokkos::ALL, i); + KokkosBatched::SerialGetrs< + KokkosBatched::Trans::NoTranspose, + KokkosBatched::Algo::Getrs::Unblocked>:: + invoke(a_device, ipiv_device, sub_b); + }); } - Kokkos::deep_copy(b, b_host); } }; diff --git a/include/ddc/kernels/splines/splines_linear_problem_maker.hpp b/include/ddc/kernels/splines/splines_linear_problem_maker.hpp index 3823ac89c..8f0ff6f52 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_maker.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_maker.hpp @@ -8,6 +8,7 @@ #include #include "splines_linear_problem_2x2_blocks.hpp" +#include "splines_linear_problem_3x3_blocks.hpp" #include "splines_linear_problem_band.hpp" #include "splines_linear_problem_dense.hpp" #include "splines_linear_problem_pds_band.hpp" @@ -65,15 +66,16 @@ class SplinesLinearProblemMaker } /** - * @brief Construct a 2x2-blocks linear problem with band "main" block (the one called - * Q in SplinesLinearProblem2x2Blocks). + * @brief Construct a 2x2-blocks or 3x3-blocks linear problem with band "main" block (the one called + * Q in SplinesLinearProblem2x2Blocks and SplinesLinearProblem3x3Blocks). * * @tparam the Kokkos::ExecutionSpace on which matrix-related operation will be performed. * @param n The size of one of the dimensions of the whole square matrix. * @param kl The number of subdiagonals in the band block. * @param ku The number of superdiagonals in the band block. * @param pds A boolean indicating if the band block is positive-definite symetric or not. - * @param bottom_right_size The size of one of the dimensions of the bottom-right block. + * @param bottom_right_size The size of one of the dimensions of the bottom-right square block. + * @param top_left_size The size of one of the dimensions of the top-left square block. * * @return The SplinesLinearProblem instance. */ @@ -84,13 +86,51 @@ class SplinesLinearProblemMaker int const kl, int const ku, bool const pds, - int const bottom_size) + int const bottom_right_size, + int const top_left_size = 0) { - int const top_size = n - bottom_size; - std::unique_ptr> top_left_block - = make_new_band(top_size, kl, ku, pds); + int const main_size = n - top_left_size - bottom_right_size; + std::unique_ptr> main_block + = make_new_band(main_size, kl, ku, pds); + if (top_left_size == 0) { + return std::make_unique< + SplinesLinearProblem2x2Blocks>(n, std::move(main_block)); + } return std::make_unique< - SplinesLinearProblem2x2Blocks>(n, std::move(top_left_block)); + SplinesLinearProblem3x3Blocks>(n, top_left_size, std::move(main_block)); + } + + /** + * @brief Construct a 2x2-blocks linear problem with band "main" block (the one called + * Q in SplinesLinearProblem2x2Blocks) and other blocks containing the "periodic parts" of + * a periodic band matrix. + * + * It simply calls make_new_block_matrix_with_band_main_block with bottom_size being + * max(kl, ku) (except if the alloation would be higher than instantiating a SplinesLinearProblemDense). + * + * @tparam the Kokkos::ExecutionSpace on which matrix-related operation will be performed. + * @param n The size of one of the dimensions of the whole square matrix. + * @param kl The number of subdiagonals in the band block. + * @param ku The number of superdiagonals in the band block. + * @param pds A boolean indicating if the band block is positive-definite symetric or not. + * + * @return The SplinesLinearProblem instance. + */ + template + static std::unique_ptr> make_new_periodic_band_matrix( + int const n, + int const kl, + int const ku, + bool const pds) + { + int const bottom_size = std::max(kl, ku); + int const top_size = std::max(0, n - bottom_size); + + if (bottom_size * (n + top_size) + (2 * kl + ku + 1) * top_size >= n * n) { + return std::make_unique>(n); + } + + return make_new_block_matrix_with_band_main_block(n, kl, ku, pds, bottom_size); } /** diff --git a/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp b/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp index 052429d34..5fdcb1696 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp @@ -8,12 +8,17 @@ #include #include +#include + #if __has_include() #include #else #include #endif +#include +#include + #include "splines_linear_problem.hpp" namespace ddc::detail { @@ -39,7 +44,8 @@ class SplinesLinearProblemPDSBand : public SplinesLinearProblem using SplinesLinearProblem::size; protected: - Kokkos::View m_q; // pds band matrix representation + Kokkos::DualView + m_q; // pds band matrix representation public: /** @@ -54,7 +60,7 @@ class SplinesLinearProblemPDSBand : public SplinesLinearProblem { assert(m_q.extent(0) <= mat_size); - Kokkos::deep_copy(m_q, 0.); + Kokkos::deep_copy(m_q.h_view, 0.); } double get_element(std::size_t i, std::size_t j) const override @@ -67,7 +73,7 @@ class SplinesLinearProblemPDSBand : public SplinesLinearProblem std::swap(i, j); } if (j - i < m_q.extent(0)) { - return m_q(j - i, i); + return m_q.h_view(j - i, i); } else { return 0.0; } @@ -83,7 +89,7 @@ class SplinesLinearProblemPDSBand : public SplinesLinearProblem std::swap(i, j); } if (j - i < m_q.extent(0)) { - m_q(j - i, i) = aij; + m_q.h_view(j - i, i) = aij; } else { assert(std::fabs(aij) < 1e-20); } @@ -101,14 +107,18 @@ class SplinesLinearProblemPDSBand : public SplinesLinearProblem 'L', size(), m_q.extent(0) - 1, - m_q.data(), - m_q.stride( - 0) // m_q.stride(0) if LAPACK_ROW_MAJOR, m_q.stride(1) if LAPACK_COL_MAJOR + m_q.h_view.data(), + m_q.h_view.stride( + 0) // m_q.h_view.stride(0) if LAPACK_ROW_MAJOR, m_q.h_view.stride(1) if LAPACK_COL_MAJOR ); if (info != 0) { throw std::runtime_error( "LAPACKE_dpbtrf failed with error code " + std::to_string(info)); } + + // Push on device + m_q.modify_host(); + m_q.sync_device(); } /** @@ -123,24 +133,17 @@ class SplinesLinearProblemPDSBand : public SplinesLinearProblem { assert(b.extent(0) == size()); - auto b_host = create_mirror_view(Kokkos::DefaultHostExecutionSpace(), b); - Kokkos::deep_copy(b_host, b); - int const info = LAPACKE_dpbtrs( - LAPACK_ROW_MAJOR, - 'L', - b_host.extent(0), - m_q.extent(0) - 1, - b_host.extent(1), - m_q.data(), - m_q.stride( - 0), // m_q.stride(0) if LAPACK_ROW_MAJOR, m_q.stride(1) if LAPACK_COL_MAJOR - b_host.data(), - b_host.stride(0)); - if (info != 0) { - throw std::runtime_error( - "LAPACKE_dpbtrs failed with error code " + std::to_string(info)); - } - Kokkos::deep_copy(b, b_host); + auto q_device = m_q.d_view; + Kokkos::RangePolicy policy(0, b.extent(1)); + Kokkos::parallel_for( + "pbtrs", + policy, + KOKKOS_CLASS_LAMBDA(const int i) { + auto sub_b = Kokkos::subview(b, Kokkos::ALL, i); + KokkosBatched::SerialPbtrs< + KokkosBatched::Uplo::Lower, + KokkosBatched::Algo::Pbtrs::Unblocked>::invoke(q_device, sub_b); + }); } }; diff --git a/include/ddc/kernels/splines/splines_linear_problem_pds_tridiag.hpp b/include/ddc/kernels/splines/splines_linear_problem_pds_tridiag.hpp index c7067958c..ddc1710e3 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_pds_tridiag.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_pds_tridiag.hpp @@ -14,6 +14,9 @@ #include #endif +#include +#include + #include "splines_linear_problem.hpp" namespace ddc::detail { @@ -39,7 +42,8 @@ class SplinesLinearProblemPDSTridiag : public SplinesLinearProblem using SplinesLinearProblem::size; protected: - Kokkos::View m_q; // pds band matrix representation + Kokkos::DualView + m_q; // pds tridiagonal matrix representation public: /** @@ -51,7 +55,7 @@ class SplinesLinearProblemPDSTridiag : public SplinesLinearProblem : SplinesLinearProblem(mat_size) , m_q("q", 2, mat_size) { - Kokkos::deep_copy(m_q, 0.); + Kokkos::deep_copy(m_q.h_view, 0.); } double get_element(std::size_t i, std::size_t j) const override @@ -64,7 +68,7 @@ class SplinesLinearProblemPDSTridiag : public SplinesLinearProblem std::swap(i, j); } if (j - i < 2) { - return m_q(j - i, i); + return m_q.h_view(j - i, i); } else { return 0.0; } @@ -80,7 +84,7 @@ class SplinesLinearProblemPDSTridiag : public SplinesLinearProblem std::swap(i, j); } if (j - i < 2) { - m_q(j - i, i) = aij; + m_q.h_view(j - i, i) = aij; } else { assert(std::fabs(aij) < 1e-20); } @@ -93,11 +97,18 @@ class SplinesLinearProblemPDSTridiag : public SplinesLinearProblem */ void setup_solver() override { - int const info = LAPACKE_dpttrf(size(), m_q.data(), m_q.data() + m_q.stride(0)); + int const info = LAPACKE_dpttrf( + size(), + m_q.h_view.data(), + m_q.h_view.data() + m_q.h_view.stride(0)); if (info != 0) { throw std::runtime_error( "LAPACKE_dpttrf failed with error code " + std::to_string(info)); } + + // Push on device + m_q.modify_host(); + m_q.sync_device(); } /** @@ -111,22 +122,18 @@ class SplinesLinearProblemPDSTridiag : public SplinesLinearProblem void solve(MultiRHS b, bool const) const override { assert(b.extent(0) == size()); - - auto b_host = create_mirror_view(Kokkos::DefaultHostExecutionSpace(), b); - Kokkos::deep_copy(b_host, b); - int const info = LAPACKE_dpttrs( - LAPACK_ROW_MAJOR, - b_host.extent(0), - b_host.extent(1), - m_q.data(), - m_q.data() + m_q.stride(0), - b_host.data(), - b_host.stride(0)); - if (info != 0) { - throw std::runtime_error( - "LAPACKE_dpttrs failed with error code " + std::to_string(info)); - } - Kokkos::deep_copy(b, b_host); + auto q_device = m_q.d_view; + auto d = Kokkos::subview(q_device, 0, Kokkos::ALL); + auto e = Kokkos::subview(q_device, 1, Kokkos::pair(0, q_device.extent(1) - 1)); + Kokkos::RangePolicy policy(0, b.extent(1)); + Kokkos::parallel_for( + "pttrs", + policy, + KOKKOS_CLASS_LAMBDA(const int i) { + auto sub_b = Kokkos::subview(b, Kokkos::ALL, i); + KokkosBatched::SerialPttrs< + KokkosBatched::Algo::Pttrs::Unblocked>::invoke(d, e, sub_b); + }); } }; diff --git a/vendor/benchmark b/vendor/benchmark index 60b16f11a..2fa4b26e5 160000 --- a/vendor/benchmark +++ b/vendor/benchmark @@ -1 +1 @@ -Subproject commit 60b16f11a30146ac825b7d99be0b9887c24b254a +Subproject commit 2fa4b26e5825d0b17577ae038c3b75e2d6b5418b diff --git a/vendor/kokkos-kernels b/vendor/kokkos-kernels new file mode 160000 index 000000000..434e56d4e --- /dev/null +++ b/vendor/kokkos-kernels @@ -0,0 +1 @@ +Subproject commit 434e56d4e7b7f8cc3fa25b8c02f4800397d59367 From 7222a3dbc9aeb3a57e9eb4b2339b7f346ca34a98 Mon Sep 17 00:00:00 2001 From: Yuuichi Asahi Date: Tue, 11 Jun 2024 09:49:39 +0200 Subject: [PATCH 136/189] rebase --- include/ddc/kernels/splines/spline_builder.hpp | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index c5b375f09..ddcb420bd 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -249,7 +249,11 @@ class SplineBuilder /** @brief Move-assigns * * @param x An rvalue to another SplineBuilder. +<<<<<<< HEAD * @return A reference to the moved SplineBuilder +======= + * @return A reference to this object. +>>>>>>> f7ebfb6 (SplineBuilder doc (#409)) */ SplineBuilder& operator=(SplineBuilder&& x) = default; From 30b5bead44c043c32821787013530c9ed1c57113 Mon Sep 17 00:00:00 2001 From: Thomas Padioleau Date: Fri, 7 Jun 2024 11:04:53 +0200 Subject: [PATCH 137/189] Update extrapolation_rule.cpp --- tests/splines/extrapolation_rule.cpp | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/tests/splines/extrapolation_rule.cpp b/tests/splines/extrapolation_rule.cpp index db7a4b035..57455305a 100644 --- a/tests/splines/extrapolation_rule.cpp +++ b/tests/splines/extrapolation_rule.cpp @@ -374,10 +374,6 @@ static void ExtrapolationRuleSplineTest() vals.domain(), vals.template domain>()))::discrete_element_type e_without_interest(e); - typename decltype(ddc::remove_dims_of( - vals.domain(), - vals.template domain, IDim>())):: - discrete_element_type e_batch(e); double tmp; if (ddc::select(coords_eval(e)) > xN()) { #if defined(BC_PERIODIC) @@ -385,6 +381,10 @@ static void ExtrapolationRuleSplineTest() vals.template domain>().back(), e_without_interest)); #else + typename decltype(ddc::remove_dims_of( + vals.domain(), + vals.template domain, IDim>())):: + discrete_element_type e_batch(e); tmp = vals(ddc::DiscreteElement...>( vals.template domain>().back(), vals.template domain>().back(), From 2977ce6a2135ca67948527bc826d9a19f75d690d Mon Sep 17 00:00:00 2001 From: Thomas Padioleau Date: Fri, 7 Jun 2024 12:42:36 +0200 Subject: [PATCH 138/189] Fix array-bounds warnings --- tests/splines/polynomial_evaluator.hpp | 9 +++------ 1 file changed, 3 insertions(+), 6 deletions(-) diff --git a/tests/splines/polynomial_evaluator.hpp b/tests/splines/polynomial_evaluator.hpp index 466e9b893..4aa65bcad 100644 --- a/tests/splines/polynomial_evaluator.hpp +++ b/tests/splines/polynomial_evaluator.hpp @@ -22,16 +22,13 @@ struct PolynomialEvaluator private: std::array m_coeffs; - int const m_degree; double const m_xN; public: template - Evaluator(Domain domain) - : m_degree(Degree) - , m_xN(std::max(std::abs(rmin(domain)), std::abs(rmax(domain)))) + Evaluator(Domain domain) : m_xN(std::max(std::abs(rmin(domain)), std::abs(rmax(domain)))) { - for (int i(0); i < m_degree + 1; ++i) { + for (int i(0); i < Degree + 1; ++i) { m_coeffs[i] = double(rand() % 100) / 100.0; } } @@ -75,7 +72,7 @@ struct PolynomialEvaluator { double result(0.0); int start = derivative < 0 ? 0 : derivative; - for (int i(start); i < m_degree + 1; ++i) { + for (int i(start); i < Degree + 1; ++i) { double v = double(falling_factorial(i, derivative)) * Kokkos::pow(x, i - derivative); result += m_coeffs[i] * v; From 3786fdb63fd310c007bfa4fb3716b2e24db6b7ed Mon Sep 17 00:00:00 2001 From: Thomas Padioleau Date: Fri, 7 Jun 2024 16:05:42 +0200 Subject: [PATCH 139/189] Update tests.yml (#482) --- .github/workflows/tests.yml | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/.github/workflows/tests.yml b/.github/workflows/tests.yml index 32c5629c1..d93488c8d 100644 --- a/.github/workflows/tests.yml +++ b/.github/workflows/tests.yml @@ -159,9 +159,7 @@ jobs: -DKokkos_ENABLE_DEPRECATED_CODE_4=OFF \ -DKokkos_ENABLE_DEPRECATION_WARNINGS=OFF \ -DCMAKE_CXX_FLAGS="\ - -Wall -Wextra -Wpedantic -Wno-sign-compare \ - -Werror=vla \ - -Werror=implicit-fallthrough \ + -Werror -Wall -Wextra -Wpedantic -Wno-sign-compare \ ${CMAKE_CXX_FLAGS}" \ ${EXTRA_CMAKE_FLAGS} \ /src From ac2ce559052b0f7324e53eeba1c59087232e973e Mon Sep 17 00:00:00 2001 From: Thomas Padioleau Date: Fri, 7 Jun 2024 17:56:09 +0200 Subject: [PATCH 140/189] Update cmake calls in the CI (#483) --- .github/workflows/gyselalibxx.yml | 12 ++++++------ .github/workflows/pages.yml | 14 ++++++++------ .github/workflows/tests.yml | 18 ++++++++++-------- 3 files changed, 24 insertions(+), 20 deletions(-) diff --git a/.github/workflows/gyselalibxx.yml b/.github/workflows/gyselalibxx.yml index 97e8c2ae9..ea45c2247 100644 --- a/.github/workflows/gyselalibxx.yml +++ b/.github/workflows/gyselalibxx.yml @@ -25,9 +25,9 @@ jobs: cat<<-EOF > run.sh set -xe git config --global --add safe.directory /src/vendor/kokkos - cmake -DCMAKE_CXX_FLAGS=-Wall -DBUILD_BENCHMARKS=ON /src - make -j 2 VERBOSE=1 - ctest --output-on-failure --timeout 5 -LE test_on_Release_only + cmake -DCMAKE_CXX_FLAGS=-Wall -DBUILD_BENCHMARKS=ON -B build -S /src + cmake --build build --parallel 2 --verbose + ctest --test-dir build --output-on-failure --timeout 5 -LE test_on_Release_only EOF docker run -v ${PWD}:/src:ro ghcr.io/gyselax/voicexx_env bash /src/run.sh continue-on-error: true @@ -51,9 +51,9 @@ jobs: cat<<-EOF > run.sh set -xe git config --global --add safe.directory /src/vendor/kokkos - cmake -DCMAKE_CXX_FLAGS=-Wall -DBUILD_BENCHMARKS=ON -DCMAKE_BUILD_TYPE=Release /src - make -j 2 VERBOSE=1 - ctest --output-on-failure --timeout 5 + cmake -DCMAKE_CXX_FLAGS=-Wall -DBUILD_BENCHMARKS=ON -DCMAKE_BUILD_TYPE=Release -B build -S /src + cmake --build build --parallel 2 --verbose + ctest --test-dir build --output-on-failure --timeout 5 EOF docker run -v ${PWD}:/src:ro ghcr.io/gyselax/voicexx_env bash /src/run.sh continue-on-error: true diff --git a/.github/workflows/pages.yml b/.github/workflows/pages.yml index 6b55abac7..aa3ab8016 100644 --- a/.github/workflows/pages.yml +++ b/.github/workflows/pages.yml @@ -97,9 +97,10 @@ jobs: -DDOXYGEN_WARN_AS_ERROR=NO \ -DMDSPAN_CXX_STANDARD=20 \ -DKokkos_ENABLE_DEPRECATION_WARNINGS=OFF \ - /src - cmake --build . --verbose --target doc - mv docs/doxygen.log /src/docs_out/doxygen.log + -B build \ + -S /src + cmake --build build --verbose --target doc + mv build/docs/doxygen.log /src/docs_out/doxygen.log EOF mkdir docs_out chmod a+rwx docs_out @@ -150,9 +151,10 @@ jobs: -DCMAKE_CXX_STANDARD=20 \ -DMDSPAN_CXX_STANDARD=20 \ -DKokkos_ENABLE_DEPRECATION_WARNINGS=OFF \ - /src - cmake --build . --verbose --target doc - mv docs/html /src/docs_out + -B build \ + -S /src + cmake --build build --verbose --target doc + mv build/docs/html /src/docs_out EOF mkdir docs_out chmod a+rwx docs_out diff --git a/.github/workflows/tests.yml b/.github/workflows/tests.yml index d93488c8d..985df57dd 100644 --- a/.github/workflows/tests.yml +++ b/.github/workflows/tests.yml @@ -162,11 +162,12 @@ jobs: -Werror -Wall -Wextra -Wpedantic -Wno-sign-compare \ ${CMAKE_CXX_FLAGS}" \ ${EXTRA_CMAKE_FLAGS} \ - /src - make -j 2 + -B build \ + -S /src + cmake --build build --parallel 2 case "${{matrix.backend}}" in 'cpu-'*) - ctest -j 2 --output-on-failure --timeout 5 --output-junit tests.xml + ctest --test-dir build --parallel 2 --output-on-failure --timeout 5 --output-junit tests.xml ;; esac EOF @@ -225,10 +226,11 @@ jobs: -DKokkos_ENABLE_DEPRECATED_CODE_4=OFF \ -DKokkos_ENABLE_DEPRECATION_WARNINGS=OFF \ -DCMAKE_CXX_FLAGS="-fsanitize=undefined -fno-omit-frame-pointer" \ - /src - make -j 2 + -B build \ + -S /src + cmake --build build --parallel 2 export UBSAN_OPTIONS=print_stacktrace=1,halt_on_error=1,suppressions=/src/ubsan.supp - ctest -j 2 --output-on-failure --timeout 5 --output-junit tests.xml + ctest --test-dir build --parallel 2 --output-on-failure --timeout 5 --output-junit tests.xml EOF docker run \ --cidfile='docker.cid' \ @@ -279,8 +281,8 @@ jobs: -DMDSPAN_CXX_STANDARD=17 \ -DKokkos_ENABLE_DEPRECATED_CODE_4=OFF \ -DKokkos_ENABLE_DEPRECATION_WARNINGS=OFF \ - -S /src \ - -B build + -B build \ + -S /src find /src/benchmarks /src/examples /src/tests -name '*.cpp' -exec clang-tidy-14 -p build -header-filter="(/src/include/ddc/.*|/src/tests/.*)" '{}' '+' EOF docker run \ From 3d663e5780b7649b70b2319c5bbd06d4a8f1af6b Mon Sep 17 00:00:00 2001 From: Thomas Padioleau Date: Fri, 7 Jun 2024 22:03:33 +0200 Subject: [PATCH 141/189] Preinstall dependencies (#484) --- .github/workflows/tests.yml | 70 ++++++++++++++++++++++++++++++++----- 1 file changed, 62 insertions(+), 8 deletions(-) diff --git a/.github/workflows/tests.yml b/.github/workflows/tests.yml index 985df57dd..d3a60cba7 100644 --- a/.github/workflows/tests.yml +++ b/.github/workflows/tests.yml @@ -131,40 +131,94 @@ jobs: 'cuda') export CC=${CUDA_GCC} export CXX=${CUDA_GXX} - EXTRA_CMAKE_FLAGS="-DKokkos_ENABLE_CUDA=ON -DKokkos_ARCH_AMPERE80=ON -DKokkos_ENABLE_LIBDL=OFF" + EXTRA_CMAKE_FLAGS="-DKokkos_ENABLE_CUDA=ON -DKokkos_ENABLE_CUDA_CONSTEXPR=ON -DKokkos_ENABLE_CUDA_RELOCATABLE_DEVICE_CODE=ON -DKokkos_ARCH_AMPERE80=ON -DKokkos_ENABLE_LIBDL=OFF" ;; 'hip') export CC=hipcc export CXX=hipcc - EXTRA_CMAKE_FLAGS="-DKokkos_ENABLE_HIP=ON -DKokkos_ENABLE_ROCTHRUST=OFF -DKokkos_ARCH_VEGA90A=ON -DCMAKE_PREFIX_PATH=/opt/rocm" + export CMAKE_PREFIX_PATH=/opt/rocm + EXTRA_CMAKE_FLAGS="-DKokkos_ENABLE_HIP=ON -DKokkos_ENABLE_HIP_RELOCATABLE_DEVICE_CODE=ON -DKokkos_ENABLE_ROCTHRUST=OFF -DKokkos_ARCH_VEGA90A=ON" ;; 'cpu-clang') export CC=clang export CXX=clang++ + DDC_CMAKE_CXX_FLAGS="-Werror=extra-semi" ;; 'cpu-gcc') export CC=gcc export CXX=g++ + DDC_CMAKE_CXX_FLAGS="-Werror=extra-semi" if [ 'xDebug' = 'x${{matrix.cmake_build_type}}' ] then - CMAKE_CXX_FLAGS="-fno-omit-frame-pointer -fsanitize=address" + DDC_CMAKE_CXX_FLAGS="${DDC_CMAKE_CXX_FLAGS} -fno-omit-frame-pointer -fsanitize=address" fi ;; esac + + export benchmark_ROOT=$PWD/opt/benchmark + export GTest_ROOT=$PWD/opt/gtest + export Kokkos_ROOT=$PWD/opt/kokkos + export mdspan_ROOT=$PWD/opt/mdspan + + cmake \ + -DCMAKE_BUILD_TYPE=${{matrix.cmake_build_type}} \ + -DCMAKE_CXX_STANDARD=${{matrix.cxx_version}} \ + -DBENCHMARK_ENABLE_GTEST_TESTS=OFF \ + -DBENCHMARK_ENABLE_TESTING=OFF \ + -DBENCHMARK_INSTALL_DOCS=OFF \ + -DBENCHMARK_USE_BUNDLED_GTEST=OFF \ + -B build \ + -S /src/vendor/benchmark + cmake --build build --parallel 2 + cmake --install build --prefix $benchmark_ROOT + rm -rf build + + cmake \ + -DCMAKE_BUILD_TYPE=${{matrix.cmake_build_type}} \ + -DCMAKE_CXX_STANDARD=${{matrix.cxx_version}} \ + -B build \ + -S /src/vendor/googletest + cmake --build build --parallel 2 + cmake --install build --prefix $GTest_ROOT + rm -rf build + cmake \ - -DDDC_BUILD_BENCHMARKS=ON \ -DCMAKE_BUILD_TYPE=${{matrix.cmake_build_type}} \ -DCMAKE_CXX_STANDARD=${{matrix.cxx_version}} \ - -DMDSPAN_CXX_STANDARD=${{matrix.cxx_version}} \ -DKokkos_ENABLE_DEPRECATED_CODE_4=OFF \ -DKokkos_ENABLE_DEPRECATION_WARNINGS=OFF \ - -DCMAKE_CXX_FLAGS="\ - -Werror -Wall -Wextra -Wpedantic -Wno-sign-compare \ - ${CMAKE_CXX_FLAGS}" \ ${EXTRA_CMAKE_FLAGS} \ -B build \ + -S /src/vendor/kokkos + cmake --build build --parallel 2 + cmake --install build --prefix $Kokkos_ROOT + rm -rf build + + cmake \ + -DCMAKE_BUILD_TYPE=${{matrix.cmake_build_type}} \ + -DCMAKE_CXX_STANDARD=${{matrix.cxx_version}} \ + -DMDSPAN_CXX_STANDARD=${{matrix.cxx_version}} \ + -B build \ + -S /src/vendor/mdspan + cmake --build build --parallel 2 + cmake --install build --prefix $mdspan_ROOT + rm -rf build + + cmake \ + -DCMAKE_BUILD_TYPE=${{matrix.cmake_build_type}} \ + -DCMAKE_CXX_FLAGS="\ + -Werror -Wall -Wextra -Wpedantic -Wno-sign-compare -pedantic-errors \ + ${DDC_CMAKE_CXX_FLAGS}" \ + -DCMAKE_CXX_STANDARD=${{matrix.cxx_version}} \ + -DDDC_BUILD_BENCHMARKS=ON \ + -DDDC_benchmark_DEPENDENCY_POLICY=INSTALLED \ + -DDDC_GTest_DEPENDENCY_POLICY=INSTALLED \ + -DDDC_Kokkos_DEPENDENCY_POLICY=INSTALLED \ + -DDDC_mdspan_DEPENDENCY_POLICY=INSTALLED \ + -B build \ -S /src cmake --build build --parallel 2 + case "${{matrix.backend}}" in 'cpu-'*) ctest --test-dir build --parallel 2 --output-on-failure --timeout 5 --output-junit tests.xml From 5e1756986f9f8e931d4bc72780f841cb96f02783 Mon Sep 17 00:00:00 2001 From: Thomas Padioleau Date: Sun, 9 Jun 2024 22:20:02 +0200 Subject: [PATCH 142/189] Update workflow --- .github/workflows/tests.yml | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/.github/workflows/tests.yml b/.github/workflows/tests.yml index d3a60cba7..6415dc301 100644 --- a/.github/workflows/tests.yml +++ b/.github/workflows/tests.yml @@ -131,13 +131,13 @@ jobs: 'cuda') export CC=${CUDA_GCC} export CXX=${CUDA_GXX} - EXTRA_CMAKE_FLAGS="-DKokkos_ENABLE_CUDA=ON -DKokkos_ENABLE_CUDA_CONSTEXPR=ON -DKokkos_ENABLE_CUDA_RELOCATABLE_DEVICE_CODE=ON -DKokkos_ARCH_AMPERE80=ON -DKokkos_ENABLE_LIBDL=OFF" + EXTRA_CMAKE_FLAGS="-DKokkos_ENABLE_CUDA=ON -DKokkos_ENABLE_CUDA_CONSTEXPR=ON -DKokkos_ENABLE_CUDA_RELOCATABLE_DEVICE_CODE=ON -DKokkos_ARCH_AMPERE80=ON" ;; 'hip') export CC=hipcc export CXX=hipcc export CMAKE_PREFIX_PATH=/opt/rocm - EXTRA_CMAKE_FLAGS="-DKokkos_ENABLE_HIP=ON -DKokkos_ENABLE_HIP_RELOCATABLE_DEVICE_CODE=ON -DKokkos_ENABLE_ROCTHRUST=OFF -DKokkos_ARCH_VEGA90A=ON" + EXTRA_CMAKE_FLAGS="-DKokkos_ENABLE_HIP=ON -DKokkos_ENABLE_HIP_RELOCATABLE_DEVICE_CODE=ON -DKokkos_ENABLE_ROCTHRUST=OFF -DKokkos_ARCH_AMD_GFX90A=ON" ;; 'cpu-clang') export CC=clang @@ -187,6 +187,7 @@ jobs: -DCMAKE_CXX_STANDARD=${{matrix.cxx_version}} \ -DKokkos_ENABLE_DEPRECATED_CODE_4=OFF \ -DKokkos_ENABLE_DEPRECATION_WARNINGS=OFF \ + -DKokkos_ENABLE_SERIAL=ON \ ${EXTRA_CMAKE_FLAGS} \ -B build \ -S /src/vendor/kokkos From 8c2a5ccf53ba453849e98341f287eaf43782f929 Mon Sep 17 00:00:00 2001 From: Thomas Padioleau Date: Mon, 10 Jun 2024 07:37:13 +0200 Subject: [PATCH 143/189] Set error on old style cast and use static_cast (#485) --- .github/workflows/tests.yml | 4 ++-- include/ddc/kernels/fft.hpp | 14 +++++++------- include/ddc/kernels/splines/spline_builder.hpp | 2 +- .../splines/splines_linear_problem_band.hpp | 8 ++++++-- tests/splines/batched_2d_spline_builder.cpp | 4 ++-- tests/splines/matrix.cpp | 4 +++- 6 files changed, 21 insertions(+), 15 deletions(-) diff --git a/.github/workflows/tests.yml b/.github/workflows/tests.yml index 6415dc301..200a7a666 100644 --- a/.github/workflows/tests.yml +++ b/.github/workflows/tests.yml @@ -142,12 +142,12 @@ jobs: 'cpu-clang') export CC=clang export CXX=clang++ - DDC_CMAKE_CXX_FLAGS="-Werror=extra-semi" + DDC_CMAKE_CXX_FLAGS="-Werror=extra-semi -Werror=old-style-cast" ;; 'cpu-gcc') export CC=gcc export CXX=g++ - DDC_CMAKE_CXX_FLAGS="-Werror=extra-semi" + DDC_CMAKE_CXX_FLAGS="-Werror=extra-semi -Werror=old-style-cast" if [ 'xDebug' = 'x${{matrix.cmake_build_type}}' ] then DDC_CMAKE_CXX_FLAGS="${DDC_CMAKE_CXX_FLAGS} -fno-omit-frame-pointer -fsanitize=address" diff --git a/include/ddc/kernels/fft.hpp b/include/ddc/kernels/fft.hpp index 5a2f3e443..d08b0c2e1 100644 --- a/include/ddc/kernels/fft.hpp +++ b/include/ddc/kernels/fft.hpp @@ -379,7 +379,7 @@ void core( (is_uniform_point_sampling_v && ...), "DDimX dimensions should derive from UniformPointSampling"); - std::array n = {(int)ddc::get(mesh.extents())...}; + std::array n = {static_cast(ddc::get(mesh.extents()))...}; int idist = 1; int odist = 1; for (std::size_t i = 0; i < sizeof...(DDimX); i++) { @@ -398,15 +398,15 @@ void core( _fftw_plan plan = _fftw_plan_many_dft( kwargs.direction == ddc::FFT_Direction::FORWARD ? FFTW_FORWARD : FFTW_BACKWARD, FFTW_ESTIMATE, - (int)sizeof...(DDimX), + static_cast(sizeof...(DDimX)), n.data(), 1, reinterpret_cast::type*>(in_data), - (int*)NULL, + static_cast(NULL), 1, idist, reinterpret_cast::type*>(out_data), - (int*)NULL, + static_cast(NULL), 1, odist); if constexpr (std::is_same_v, float>) { @@ -430,15 +430,15 @@ void core( _fftw_plan plan = _fftw_plan_many_dft( kwargs.direction == ddc::FFT_Direction::FORWARD ? FFTW_FORWARD : FFTW_BACKWARD, FFTW_ESTIMATE, - (int)sizeof...(DDimX), + static_cast(sizeof...(DDimX)), n.data(), 1, reinterpret_cast::type*>(in_data), - (int*)NULL, + static_cast(NULL), 1, idist, reinterpret_cast::type*>(out_data), - (int*)NULL, + static_cast(NULL), 1, odist); if constexpr (std::is_same_v, float>) { diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index ddcb420bd..118bb39a1 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -703,7 +703,7 @@ void SplineBuilder< for (std::size_t s = 0; s < bsplines_type::degree() + 1; ++s) { int const j = ddc::detail:: modulo(int(jmin.uid() - m_offset + s), - (int)ddc::discrete_space().nbasis()); + static_cast(ddc::discrete_space().nbasis())); matrix->set_element(ix.uid() - start + s_nbc_xmin, j, values(s)); } }); diff --git a/include/ddc/kernels/splines/splines_linear_problem_band.hpp b/include/ddc/kernels/splines/splines_linear_problem_band.hpp index 9ef93abf1..6615ea19a 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_band.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_band.hpp @@ -90,7 +90,9 @@ class SplinesLinearProblemBand : public SplinesLinearProblem * are supported by LAPACKE. The m_kl first lines are irrelevant for the storage of * the matrix itself but required for the storage of its LU factorization. */ - if (i >= std::max((std::ptrdiff_t)0, (std::ptrdiff_t)j - (std::ptrdiff_t)m_ku) + if (i >= std:: + max(static_cast(0), + static_cast(j) - static_cast(m_ku)) && i < std::min(size(), j + m_kl + 1)) { return m_q(band_storage_row_index(i, j), j); } else { @@ -108,7 +110,9 @@ class SplinesLinearProblemBand : public SplinesLinearProblem * are supported by LAPACKE. The m_kl first lines are irrelevant for the storage of * the matrix itself but required for the storage of its LU factorization. */ - if (i >= std::max((std::ptrdiff_t)0, (std::ptrdiff_t)j - (std::ptrdiff_t)m_ku) + if (i >= std:: + max(static_cast(0), + static_cast(j) - static_cast(m_ku)) && i < std::min(size(), j + m_kl + 1)) { m_q(band_storage_row_index(i, j), j) = aij; } else { diff --git a/tests/splines/batched_2d_spline_builder.cpp b/tests/splines/batched_2d_spline_builder.cpp index b0ea9c9f7..0e4c20c0e 100644 --- a/tests/splines/batched_2d_spline_builder.cpp +++ b/tests/splines/batched_2d_spline_builder.cpp @@ -466,10 +466,10 @@ static void Batched2dSplineTest() ddc::ChunkSpan Sderiv_mixed_rhs_rhs1_cpu = Sderiv_mixed_rhs_rhs1_cpu_alloc.span_view(); for (std::size_t ii = 1; - ii < (std::size_t)derivs_domain.template extent>() + 1; + ii < static_cast(derivs_domain.template extent>()) + 1; ++ii) { for (std::size_t jj = 1; - jj < (std::size_t)derivs_domain.template extent>() + 1; + jj < static_cast(derivs_domain.template extent>()) + 1; ++jj) { Sderiv_mixed_lhs_lhs1_cpu( typename decltype(derivs_domain)::discrete_element_type(ii, jj)) diff --git a/tests/splines/matrix.cpp b/tests/splines/matrix.cpp index cf24fc038..c48cec784 100644 --- a/tests/splines/matrix.cpp +++ b/tests/splines/matrix.cpp @@ -426,7 +426,9 @@ TEST_P(MatrixSizesFixture, Sparse) for (std::size_t j(0); j < N; ++j) { if (i == j) { matrix->set_element(i, j, 3. / 4); - } else if (std::abs((std::ptrdiff_t)(j - i)) <= (std::ptrdiff_t)k) { + } else if ( + std::abs(static_cast(j - i)) + <= static_cast(k)) { matrix->set_element(i, j, -(1. / 4) / k); } } From 759ce0f51d4f5a762b5e8b404be582856ee45167 Mon Sep 17 00:00:00 2001 From: Thomas Padioleau Date: Mon, 10 Jun 2024 09:24:18 +0200 Subject: [PATCH 144/189] Modernize use nullptr (#486) * Set error on old style cast and use static_cast * Modernize use nullptr --- .clang-tidy | 2 +- include/ddc/kernels/fft.hpp | 16 ++++++++-------- 2 files changed, 9 insertions(+), 9 deletions(-) diff --git a/.clang-tidy b/.clang-tidy index 245919248..669ed9bfb 100644 --- a/.clang-tidy +++ b/.clang-tidy @@ -2,5 +2,5 @@ # # SPDX-License-Identifier: MIT --- -Checks: '-*,bugprone-reserved-identifier,hicpp-avoid-c-arrays' +Checks: '-*,bugprone-reserved-identifier,hicpp-avoid-c-arrays,modernize-use-nullptr' WarningsAsErrors: '*' diff --git a/include/ddc/kernels/fft.hpp b/include/ddc/kernels/fft.hpp index d08b0c2e1..44bac1c89 100644 --- a/include/ddc/kernels/fft.hpp +++ b/include/ddc/kernels/fft.hpp @@ -402,11 +402,11 @@ void core( n.data(), 1, reinterpret_cast::type*>(in_data), - static_cast(NULL), + static_cast(nullptr), 1, idist, reinterpret_cast::type*>(out_data), - static_cast(NULL), + static_cast(nullptr), 1, odist); if constexpr (std::is_same_v, float>) { @@ -434,11 +434,11 @@ void core( n.data(), 1, reinterpret_cast::type*>(in_data), - static_cast(NULL), + static_cast(nullptr), 1, idist, reinterpret_cast::type*>(out_data), - static_cast(NULL), + static_cast(nullptr), 1, odist); if constexpr (std::is_same_v, float>) { @@ -468,10 +468,10 @@ void core( &unmanaged_plan, // plan handle sizeof...(DDimX), n.data(), // Nx, Ny... - NULL, + nullptr, 1, idist, - NULL, + nullptr, 1, odist, cufft_transform_type(), @@ -507,10 +507,10 @@ void core( &unmanaged_plan, // plan handle sizeof...(DDimX), n.data(), // Nx, Ny... - NULL, + nullptr, 1, idist, - NULL, + nullptr, 1, odist, hipfft_transform_type(), From 40b65cfc1cc012326715485083a018a9095b4454 Mon Sep 17 00:00:00 2001 From: Thomas Padioleau Date: Mon, 10 Jun 2024 09:29:33 +0200 Subject: [PATCH 145/189] Update tests.yml --- .github/workflows/tests.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/tests.yml b/.github/workflows/tests.yml index 200a7a666..adaebb4e0 100644 --- a/.github/workflows/tests.yml +++ b/.github/workflows/tests.yml @@ -14,7 +14,7 @@ jobs: runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 - - uses: DoozyX/clang-format-lint-action@v0.13 + - uses: DoozyX/clang-format-lint-action@v0.17 with: source: 'include/ddc/ tests/ examples/' exclude: '' From 6f3eded11de53ece9f30fc187d38f713d68204a1 Mon Sep 17 00:00:00 2001 From: Yuuichi Asahi Date: Tue, 11 Jun 2024 09:13:01 +0200 Subject: [PATCH 146/189] testing KK backend --- .gitmodules | 3 + CMakeLists.txt | 10 +++ benchmarks/splines.cpp | 2 +- examples/characteristics_advection.cpp | 2 +- .../splines_linear_problem_2x2_blocks.hpp | 75 ++----------------- .../splines/splines_linear_problem_dense.hpp | 73 ++++++++++++------ .../splines_linear_problem_pds_band.hpp | 53 ++++++------- .../splines_linear_problem_pds_tridiag.hpp | 49 ++++++------ vendor/benchmark | 2 +- vendor/kokkos-kernels | 1 + 10 files changed, 128 insertions(+), 142 deletions(-) create mode 160000 vendor/kokkos-kernels diff --git a/.gitmodules b/.gitmodules index a559a2afd..f4d5668ec 100644 --- a/.gitmodules +++ b/.gitmodules @@ -15,3 +15,6 @@ [submodule "vendor/kokkos"] path = vendor/kokkos url = https://github.com/kokkos/kokkos.git +[submodule "vendor/kokkos-kernels"] + path = vendor/kokkos-kernels + url = https://github.com/yasahi-hpc/kokkos-kernels.git diff --git a/CMakeLists.txt b/CMakeLists.txt index c00a64135..7e2619487 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -253,6 +253,16 @@ if("${DDC_BUILD_KERNELS_SPLINES}") find_package(LAPACKE REQUIRED) target_link_libraries(DDC INTERFACE "${LAPACKE_LIBRARIES}") target_include_directories(DDC INTERFACE "${LAPACKE_INCLUDE_DIRS}") + + # Kokkos-kernels + set(KokkosKernels_ENABLE_ALL_COMPONENTS OFF) + set(KokkosKernels_ENABLE_COMPONENT_BLAS ON) + set(KokkosKernels_ENABLE_COMPONENT_BATCHED ON) + set(KokkosKernels_ENABLE_COMPONENT_LAPACK OFF) + set(KokkosKernels_ENABLE_TPL_BLAS ON) + set(KokkosKernels_ENABLE_TPL_LAPACK OFF) + add_subdirectory(vendor/kokkos-kernels/) + target_link_libraries(DDC INTERFACE Kokkos::kokkoskernels) endif() ## The PDI wrapper diff --git a/benchmarks/splines.cpp b/benchmarks/splines.cpp index f6bda61f0..6902b6e08 100644 --- a/benchmarks/splines.cpp +++ b/benchmarks/splines.cpp @@ -117,7 +117,7 @@ static void characteristics_advection(benchmark::State& state) DDimX, ddc::BoundCond::PERIODIC, ddc::BoundCond::PERIODIC, - ddc::SplineSolver::GINKGO, + ddc::SplineSolver::LAPACK, DDimX, DDimY> spline_builder(x_mesh, state.range(2), state.range(3)); diff --git a/examples/characteristics_advection.cpp b/examples/characteristics_advection.cpp index 77ad725fc..133c2b2e5 100644 --- a/examples/characteristics_advection.cpp +++ b/examples/characteristics_advection.cpp @@ -217,7 +217,7 @@ int main(int argc, char** argv) DDimX, ddc::BoundCond::PERIODIC, ddc::BoundCond::PERIODIC, - ddc::SplineSolver::GINKGO, + ddc::SplineSolver::LAPACK, DDimX, DDimY> spline_builder(x_mesh); diff --git a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp index fe605d71d..35d8c1e99 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp @@ -8,6 +8,7 @@ #include #include +#include #include #include "splines_linear_problem.hpp" @@ -163,72 +164,6 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem m_bottom_right_block->setup_solver(); } - /** - * @brief Compute y <- y - LinOp*x or y <- y - LinOp^t*x. - * - * [SHOULD BE PRIVATE (GPU programming limitation)] - * - * @param x - * @param y - * @param LinOp - * @param transpose - */ - void gemv_minus1_1( - MultiRHS const x, - MultiRHS const y, - Kokkos::View const - LinOp, - bool const transpose = false) const - { - assert((!transpose && LinOp.extent(0) == y.extent(0)) - || (transpose && LinOp.extent(1) == y.extent(0))); - assert((!transpose && LinOp.extent(1) == x.extent(0)) - || (transpose && LinOp.extent(0) == x.extent(0))); - assert(x.extent(1) == y.extent(1)); - - if (!transpose) { - Kokkos::parallel_for( - "gemv_minus1_1", - Kokkos::TeamPolicy(y.extent(0) * y.extent(1), Kokkos::AUTO), - KOKKOS_LAMBDA( - const typename Kokkos::TeamPolicy::member_type& teamMember) { - const int i = teamMember.league_rank() / y.extent(1); - const int j = teamMember.league_rank() % y.extent(1); - - double LinOpTimesX = 0.; - Kokkos::parallel_reduce( - Kokkos::TeamThreadRange(teamMember, x.extent(0)), - [&](const int l, double& LinOpTimesX_tmp) { - LinOpTimesX_tmp += LinOp(i, l) * x(l, j); - }, - LinOpTimesX); - Kokkos::single(Kokkos::PerTeam(teamMember), [&]() { - y(i, j) -= LinOpTimesX; - }); - }); - } else { - Kokkos::parallel_for( - "gemv_minus1_1_tr", - Kokkos::TeamPolicy(y.extent(0) * y.extent(1), Kokkos::AUTO), - KOKKOS_LAMBDA( - const typename Kokkos::TeamPolicy::member_type& teamMember) { - const int i = teamMember.league_rank() / y.extent(1); - const int j = teamMember.league_rank() % y.extent(1); - - double LinOpTimesX = 0.; - Kokkos::parallel_reduce( - Kokkos::TeamThreadRange(teamMember, x.extent(0)), - [&](const int l, double& LinOpTimesX_tmp) { - LinOpTimesX_tmp += LinOp(l, i) * x(l, j); - }, - LinOpTimesX); - Kokkos::single(Kokkos::PerTeam(teamMember), [&]() { - y(i, j) -= LinOpTimesX; - }); - }); - } - } - /** * @brief Solve the multiple right-hand sides linear problem Ax=b or its transposed version A^tx=b inplace. * @@ -261,13 +196,13 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem Kokkos::ALL); if (!transpose) { m_top_left_block->solve(b1); - gemv_minus1_1(b1, b2, m_bottom_left_block.d_view); + KokkosBlas::gemm(ExecSpace(), "N", "N", -1., m_bottom_left_block.d_view, b1, 1., b2); m_bottom_right_block->solve(b2); - gemv_minus1_1(b2, b1, m_top_right_block.d_view); + KokkosBlas::gemm(ExecSpace(), "N", "N", -1., m_top_right_block.d_view, b2, 1., b1); } else { - gemv_minus1_1(b1, b2, m_top_right_block.d_view, true); + KokkosBlas::gemm(ExecSpace(), "T", "N", -1., m_top_right_block.d_view, b1, 1., b2); m_bottom_right_block->solve(b2, true); - gemv_minus1_1(b2, b1, m_bottom_left_block.d_view, true); + KokkosBlas::gemm(ExecSpace(), "T", "N", -1., m_bottom_left_block.d_view, b2, 1., b1); m_top_left_block->solve(b1, true); } } diff --git a/include/ddc/kernels/splines/splines_linear_problem_dense.hpp b/include/ddc/kernels/splines/splines_linear_problem_dense.hpp index e36f6e9b2..504b45c2c 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_dense.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_dense.hpp @@ -8,12 +8,17 @@ #include #include +#include + #if __has_include() #include #else #include #endif +#include +#include + #include "splines_linear_problem.hpp" namespace ddc::detail { @@ -33,8 +38,8 @@ class SplinesLinearProblemDense : public SplinesLinearProblem using SplinesLinearProblem::size; protected: - Kokkos::View m_a; - Kokkos::View m_ipiv; + Kokkos::DualView m_a; + Kokkos::DualView m_ipiv; public: /** @@ -47,21 +52,21 @@ class SplinesLinearProblemDense : public SplinesLinearProblem , m_a("a", mat_size, mat_size) , m_ipiv("ipiv", mat_size) { - Kokkos::deep_copy(m_a, 0.); + Kokkos::deep_copy(m_a.h_view, 0.); } double get_element(std::size_t const i, std::size_t const j) const override { assert(i < size()); assert(j < size()); - return m_a(i, j); + return m_a.h_view(i, j); } void set_element(std::size_t const i, std::size_t const j, double const aij) override { assert(i < size()); assert(j < size()); - m_a(i, j) = aij; + m_a.h_view(i, j) = aij; } /** @@ -75,13 +80,24 @@ class SplinesLinearProblemDense : public SplinesLinearProblem LAPACK_ROW_MAJOR, size(), size(), - m_a.data(), + m_a.h_view.data(), size(), - m_ipiv.data()); + m_ipiv.h_view.data()); if (info != 0) { throw std::runtime_error( "LAPACKE_dgetrf failed with error code " + std::to_string(info)); } + + // Convert 1-based index to 0-based index + for (int i = 0; i < size(); ++i) { + m_ipiv.h_view(i) -= 1; + } + + // Push on device + m_a.modify_host(); + m_a.sync_device(); + m_ipiv.modify_host(); + m_ipiv.sync_device(); } /** @@ -96,23 +112,34 @@ class SplinesLinearProblemDense : public SplinesLinearProblem { assert(b.extent(0) == size()); - auto b_host = create_mirror_view(Kokkos::DefaultHostExecutionSpace(), b); - Kokkos::deep_copy(b_host, b); - int const info = LAPACKE_dgetrs( - LAPACK_ROW_MAJOR, - transpose ? 'T' : 'N', - b_host.extent(0), - b_host.extent(1), - m_a.data(), - b_host.extent(0), - m_ipiv.data(), - b_host.data(), - b_host.stride(0)); - if (info != 0) { - throw std::runtime_error( - "LAPACKE_dgetrs failed with error code " + std::to_string(info)); + auto a_device = m_a.d_view; + auto ipiv_device = m_ipiv.d_view; + + Kokkos::RangePolicy policy(0, b.extent(1)); + + if (transpose) { + Kokkos::parallel_for( + "gerts", + policy, + KOKKOS_LAMBDA(const int i) { + auto sub_b = Kokkos::subview(b, Kokkos::ALL, i); + KokkosBatched::SerialGetrs< + KokkosBatched::Trans::Transpose, + KokkosBatched::Algo::Getrs::Unblocked>:: + invoke(a_device, ipiv_device, sub_b); + }); + } else { + Kokkos::parallel_for( + "gerts", + policy, + KOKKOS_LAMBDA(const int i) { + auto sub_b = Kokkos::subview(b, Kokkos::ALL, i); + KokkosBatched::SerialGetrs< + KokkosBatched::Trans::NoTranspose, + KokkosBatched::Algo::Getrs::Unblocked>:: + invoke(a_device, ipiv_device, sub_b); + }); } - Kokkos::deep_copy(b, b_host); } }; diff --git a/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp b/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp index 052429d34..5fdcb1696 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp @@ -8,12 +8,17 @@ #include #include +#include + #if __has_include() #include #else #include #endif +#include +#include + #include "splines_linear_problem.hpp" namespace ddc::detail { @@ -39,7 +44,8 @@ class SplinesLinearProblemPDSBand : public SplinesLinearProblem using SplinesLinearProblem::size; protected: - Kokkos::View m_q; // pds band matrix representation + Kokkos::DualView + m_q; // pds band matrix representation public: /** @@ -54,7 +60,7 @@ class SplinesLinearProblemPDSBand : public SplinesLinearProblem { assert(m_q.extent(0) <= mat_size); - Kokkos::deep_copy(m_q, 0.); + Kokkos::deep_copy(m_q.h_view, 0.); } double get_element(std::size_t i, std::size_t j) const override @@ -67,7 +73,7 @@ class SplinesLinearProblemPDSBand : public SplinesLinearProblem std::swap(i, j); } if (j - i < m_q.extent(0)) { - return m_q(j - i, i); + return m_q.h_view(j - i, i); } else { return 0.0; } @@ -83,7 +89,7 @@ class SplinesLinearProblemPDSBand : public SplinesLinearProblem std::swap(i, j); } if (j - i < m_q.extent(0)) { - m_q(j - i, i) = aij; + m_q.h_view(j - i, i) = aij; } else { assert(std::fabs(aij) < 1e-20); } @@ -101,14 +107,18 @@ class SplinesLinearProblemPDSBand : public SplinesLinearProblem 'L', size(), m_q.extent(0) - 1, - m_q.data(), - m_q.stride( - 0) // m_q.stride(0) if LAPACK_ROW_MAJOR, m_q.stride(1) if LAPACK_COL_MAJOR + m_q.h_view.data(), + m_q.h_view.stride( + 0) // m_q.h_view.stride(0) if LAPACK_ROW_MAJOR, m_q.h_view.stride(1) if LAPACK_COL_MAJOR ); if (info != 0) { throw std::runtime_error( "LAPACKE_dpbtrf failed with error code " + std::to_string(info)); } + + // Push on device + m_q.modify_host(); + m_q.sync_device(); } /** @@ -123,24 +133,17 @@ class SplinesLinearProblemPDSBand : public SplinesLinearProblem { assert(b.extent(0) == size()); - auto b_host = create_mirror_view(Kokkos::DefaultHostExecutionSpace(), b); - Kokkos::deep_copy(b_host, b); - int const info = LAPACKE_dpbtrs( - LAPACK_ROW_MAJOR, - 'L', - b_host.extent(0), - m_q.extent(0) - 1, - b_host.extent(1), - m_q.data(), - m_q.stride( - 0), // m_q.stride(0) if LAPACK_ROW_MAJOR, m_q.stride(1) if LAPACK_COL_MAJOR - b_host.data(), - b_host.stride(0)); - if (info != 0) { - throw std::runtime_error( - "LAPACKE_dpbtrs failed with error code " + std::to_string(info)); - } - Kokkos::deep_copy(b, b_host); + auto q_device = m_q.d_view; + Kokkos::RangePolicy policy(0, b.extent(1)); + Kokkos::parallel_for( + "pbtrs", + policy, + KOKKOS_CLASS_LAMBDA(const int i) { + auto sub_b = Kokkos::subview(b, Kokkos::ALL, i); + KokkosBatched::SerialPbtrs< + KokkosBatched::Uplo::Lower, + KokkosBatched::Algo::Pbtrs::Unblocked>::invoke(q_device, sub_b); + }); } }; diff --git a/include/ddc/kernels/splines/splines_linear_problem_pds_tridiag.hpp b/include/ddc/kernels/splines/splines_linear_problem_pds_tridiag.hpp index c7067958c..ddc1710e3 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_pds_tridiag.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_pds_tridiag.hpp @@ -14,6 +14,9 @@ #include #endif +#include +#include + #include "splines_linear_problem.hpp" namespace ddc::detail { @@ -39,7 +42,8 @@ class SplinesLinearProblemPDSTridiag : public SplinesLinearProblem using SplinesLinearProblem::size; protected: - Kokkos::View m_q; // pds band matrix representation + Kokkos::DualView + m_q; // pds tridiagonal matrix representation public: /** @@ -51,7 +55,7 @@ class SplinesLinearProblemPDSTridiag : public SplinesLinearProblem : SplinesLinearProblem(mat_size) , m_q("q", 2, mat_size) { - Kokkos::deep_copy(m_q, 0.); + Kokkos::deep_copy(m_q.h_view, 0.); } double get_element(std::size_t i, std::size_t j) const override @@ -64,7 +68,7 @@ class SplinesLinearProblemPDSTridiag : public SplinesLinearProblem std::swap(i, j); } if (j - i < 2) { - return m_q(j - i, i); + return m_q.h_view(j - i, i); } else { return 0.0; } @@ -80,7 +84,7 @@ class SplinesLinearProblemPDSTridiag : public SplinesLinearProblem std::swap(i, j); } if (j - i < 2) { - m_q(j - i, i) = aij; + m_q.h_view(j - i, i) = aij; } else { assert(std::fabs(aij) < 1e-20); } @@ -93,11 +97,18 @@ class SplinesLinearProblemPDSTridiag : public SplinesLinearProblem */ void setup_solver() override { - int const info = LAPACKE_dpttrf(size(), m_q.data(), m_q.data() + m_q.stride(0)); + int const info = LAPACKE_dpttrf( + size(), + m_q.h_view.data(), + m_q.h_view.data() + m_q.h_view.stride(0)); if (info != 0) { throw std::runtime_error( "LAPACKE_dpttrf failed with error code " + std::to_string(info)); } + + // Push on device + m_q.modify_host(); + m_q.sync_device(); } /** @@ -111,22 +122,18 @@ class SplinesLinearProblemPDSTridiag : public SplinesLinearProblem void solve(MultiRHS b, bool const) const override { assert(b.extent(0) == size()); - - auto b_host = create_mirror_view(Kokkos::DefaultHostExecutionSpace(), b); - Kokkos::deep_copy(b_host, b); - int const info = LAPACKE_dpttrs( - LAPACK_ROW_MAJOR, - b_host.extent(0), - b_host.extent(1), - m_q.data(), - m_q.data() + m_q.stride(0), - b_host.data(), - b_host.stride(0)); - if (info != 0) { - throw std::runtime_error( - "LAPACKE_dpttrs failed with error code " + std::to_string(info)); - } - Kokkos::deep_copy(b, b_host); + auto q_device = m_q.d_view; + auto d = Kokkos::subview(q_device, 0, Kokkos::ALL); + auto e = Kokkos::subview(q_device, 1, Kokkos::pair(0, q_device.extent(1) - 1)); + Kokkos::RangePolicy policy(0, b.extent(1)); + Kokkos::parallel_for( + "pttrs", + policy, + KOKKOS_CLASS_LAMBDA(const int i) { + auto sub_b = Kokkos::subview(b, Kokkos::ALL, i); + KokkosBatched::SerialPttrs< + KokkosBatched::Algo::Pttrs::Unblocked>::invoke(d, e, sub_b); + }); } }; diff --git a/vendor/benchmark b/vendor/benchmark index 60b16f11a..2fa4b26e5 160000 --- a/vendor/benchmark +++ b/vendor/benchmark @@ -1 +1 @@ -Subproject commit 60b16f11a30146ac825b7d99be0b9887c24b254a +Subproject commit 2fa4b26e5825d0b17577ae038c3b75e2d6b5418b diff --git a/vendor/kokkos-kernels b/vendor/kokkos-kernels new file mode 160000 index 000000000..434e56d4e --- /dev/null +++ b/vendor/kokkos-kernels @@ -0,0 +1 @@ +Subproject commit 434e56d4e7b7f8cc3fa25b8c02f4800397d59367 From 1d2ad01934c78e714ee29da83a05baa53506fffd Mon Sep 17 00:00:00 2001 From: Yuuichi Asahi Date: Tue, 11 Jun 2024 09:47:54 +0200 Subject: [PATCH 147/189] remove 3x3 --- .../splines/splines_linear_problem_maker.hpp | 56 +++---------------- 1 file changed, 8 insertions(+), 48 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_maker.hpp b/include/ddc/kernels/splines/splines_linear_problem_maker.hpp index 8f0ff6f52..3823ac89c 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_maker.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_maker.hpp @@ -8,7 +8,6 @@ #include #include "splines_linear_problem_2x2_blocks.hpp" -#include "splines_linear_problem_3x3_blocks.hpp" #include "splines_linear_problem_band.hpp" #include "splines_linear_problem_dense.hpp" #include "splines_linear_problem_pds_band.hpp" @@ -66,16 +65,15 @@ class SplinesLinearProblemMaker } /** - * @brief Construct a 2x2-blocks or 3x3-blocks linear problem with band "main" block (the one called - * Q in SplinesLinearProblem2x2Blocks and SplinesLinearProblem3x3Blocks). + * @brief Construct a 2x2-blocks linear problem with band "main" block (the one called + * Q in SplinesLinearProblem2x2Blocks). * * @tparam the Kokkos::ExecutionSpace on which matrix-related operation will be performed. * @param n The size of one of the dimensions of the whole square matrix. * @param kl The number of subdiagonals in the band block. * @param ku The number of superdiagonals in the band block. * @param pds A boolean indicating if the band block is positive-definite symetric or not. - * @param bottom_right_size The size of one of the dimensions of the bottom-right square block. - * @param top_left_size The size of one of the dimensions of the top-left square block. + * @param bottom_right_size The size of one of the dimensions of the bottom-right block. * * @return The SplinesLinearProblem instance. */ @@ -86,51 +84,13 @@ class SplinesLinearProblemMaker int const kl, int const ku, bool const pds, - int const bottom_right_size, - int const top_left_size = 0) + int const bottom_size) { - int const main_size = n - top_left_size - bottom_right_size; - std::unique_ptr> main_block - = make_new_band(main_size, kl, ku, pds); - if (top_left_size == 0) { - return std::make_unique< - SplinesLinearProblem2x2Blocks>(n, std::move(main_block)); - } + int const top_size = n - bottom_size; + std::unique_ptr> top_left_block + = make_new_band(top_size, kl, ku, pds); return std::make_unique< - SplinesLinearProblem3x3Blocks>(n, top_left_size, std::move(main_block)); - } - - /** - * @brief Construct a 2x2-blocks linear problem with band "main" block (the one called - * Q in SplinesLinearProblem2x2Blocks) and other blocks containing the "periodic parts" of - * a periodic band matrix. - * - * It simply calls make_new_block_matrix_with_band_main_block with bottom_size being - * max(kl, ku) (except if the alloation would be higher than instantiating a SplinesLinearProblemDense). - * - * @tparam the Kokkos::ExecutionSpace on which matrix-related operation will be performed. - * @param n The size of one of the dimensions of the whole square matrix. - * @param kl The number of subdiagonals in the band block. - * @param ku The number of superdiagonals in the band block. - * @param pds A boolean indicating if the band block is positive-definite symetric or not. - * - * @return The SplinesLinearProblem instance. - */ - template - static std::unique_ptr> make_new_periodic_band_matrix( - int const n, - int const kl, - int const ku, - bool const pds) - { - int const bottom_size = std::max(kl, ku); - int const top_size = std::max(0, n - bottom_size); - - if (bottom_size * (n + top_size) + (2 * kl + ku + 1) * top_size >= n * n) { - return std::make_unique>(n); - } - - return make_new_block_matrix_with_band_main_block(n, kl, ku, pds, bottom_size); + SplinesLinearProblem2x2Blocks>(n, std::move(top_left_block)); } /** From f4517ebae2793952dc8fe707f7457e64f4dd1884 Mon Sep 17 00:00:00 2001 From: Yuuichi Asahi Date: Tue, 11 Jun 2024 10:01:04 +0200 Subject: [PATCH 148/189] rebased on lapack-backend --- .../ddc/kernels/splines/spline_builder.hpp | 6 +- .../splines/splines_linear_problem_maker.hpp | 56 ++++++++++++++++--- 2 files changed, 49 insertions(+), 13 deletions(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index 118bb39a1..c5b375f09 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -249,11 +249,7 @@ class SplineBuilder /** @brief Move-assigns * * @param x An rvalue to another SplineBuilder. -<<<<<<< HEAD * @return A reference to the moved SplineBuilder -======= - * @return A reference to this object. ->>>>>>> f7ebfb6 (SplineBuilder doc (#409)) */ SplineBuilder& operator=(SplineBuilder&& x) = default; @@ -703,7 +699,7 @@ void SplineBuilder< for (std::size_t s = 0; s < bsplines_type::degree() + 1; ++s) { int const j = ddc::detail:: modulo(int(jmin.uid() - m_offset + s), - static_cast(ddc::discrete_space().nbasis())); + (int)ddc::discrete_space().nbasis()); matrix->set_element(ix.uid() - start + s_nbc_xmin, j, values(s)); } }); diff --git a/include/ddc/kernels/splines/splines_linear_problem_maker.hpp b/include/ddc/kernels/splines/splines_linear_problem_maker.hpp index 3823ac89c..8f0ff6f52 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_maker.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_maker.hpp @@ -8,6 +8,7 @@ #include #include "splines_linear_problem_2x2_blocks.hpp" +#include "splines_linear_problem_3x3_blocks.hpp" #include "splines_linear_problem_band.hpp" #include "splines_linear_problem_dense.hpp" #include "splines_linear_problem_pds_band.hpp" @@ -65,15 +66,16 @@ class SplinesLinearProblemMaker } /** - * @brief Construct a 2x2-blocks linear problem with band "main" block (the one called - * Q in SplinesLinearProblem2x2Blocks). + * @brief Construct a 2x2-blocks or 3x3-blocks linear problem with band "main" block (the one called + * Q in SplinesLinearProblem2x2Blocks and SplinesLinearProblem3x3Blocks). * * @tparam the Kokkos::ExecutionSpace on which matrix-related operation will be performed. * @param n The size of one of the dimensions of the whole square matrix. * @param kl The number of subdiagonals in the band block. * @param ku The number of superdiagonals in the band block. * @param pds A boolean indicating if the band block is positive-definite symetric or not. - * @param bottom_right_size The size of one of the dimensions of the bottom-right block. + * @param bottom_right_size The size of one of the dimensions of the bottom-right square block. + * @param top_left_size The size of one of the dimensions of the top-left square block. * * @return The SplinesLinearProblem instance. */ @@ -84,13 +86,51 @@ class SplinesLinearProblemMaker int const kl, int const ku, bool const pds, - int const bottom_size) + int const bottom_right_size, + int const top_left_size = 0) { - int const top_size = n - bottom_size; - std::unique_ptr> top_left_block - = make_new_band(top_size, kl, ku, pds); + int const main_size = n - top_left_size - bottom_right_size; + std::unique_ptr> main_block + = make_new_band(main_size, kl, ku, pds); + if (top_left_size == 0) { + return std::make_unique< + SplinesLinearProblem2x2Blocks>(n, std::move(main_block)); + } return std::make_unique< - SplinesLinearProblem2x2Blocks>(n, std::move(top_left_block)); + SplinesLinearProblem3x3Blocks>(n, top_left_size, std::move(main_block)); + } + + /** + * @brief Construct a 2x2-blocks linear problem with band "main" block (the one called + * Q in SplinesLinearProblem2x2Blocks) and other blocks containing the "periodic parts" of + * a periodic band matrix. + * + * It simply calls make_new_block_matrix_with_band_main_block with bottom_size being + * max(kl, ku) (except if the alloation would be higher than instantiating a SplinesLinearProblemDense). + * + * @tparam the Kokkos::ExecutionSpace on which matrix-related operation will be performed. + * @param n The size of one of the dimensions of the whole square matrix. + * @param kl The number of subdiagonals in the band block. + * @param ku The number of superdiagonals in the band block. + * @param pds A boolean indicating if the band block is positive-definite symetric or not. + * + * @return The SplinesLinearProblem instance. + */ + template + static std::unique_ptr> make_new_periodic_band_matrix( + int const n, + int const kl, + int const ku, + bool const pds) + { + int const bottom_size = std::max(kl, ku); + int const top_size = std::max(0, n - bottom_size); + + if (bottom_size * (n + top_size) + (2 * kl + ku + 1) * top_size >= n * n) { + return std::make_unique>(n); + } + + return make_new_block_matrix_with_band_main_block(n, kl, ku, pds, bottom_size); } /** From 704f4bdda1385696cb0d80b9e12770f311dcd1d2 Mon Sep 17 00:00:00 2001 From: Baptiste Legouix Date: Mon, 17 Jun 2024 11:39:29 +0200 Subject: [PATCH 149/189] Update include/ddc/kernels/splines/splines_linear_problem_maker.hpp Co-authored-by: Thomas Padioleau --- include/ddc/kernels/splines/splines_linear_problem_maker.hpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_maker.hpp b/include/ddc/kernels/splines/splines_linear_problem_maker.hpp index 541b43858..c28250d65 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_maker.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_maker.hpp @@ -99,7 +99,7 @@ class SplinesLinearProblemMaker * a periodic band matrix. * * It simply calls make_new_block_matrix_with_band_main_block with bottom_size being - * max(kl, ku) (except if the alloation would be higher than instantiating a SplinesLinearProblemDense). + * max(kl, ku) (except if the allocation would be higher than instantiating a SplinesLinearProblemDense). * * @tparam the Kokkos::ExecutionSpace on which matrix-related operation will be performed. * @param n The size of one of the dimensions of the whole square matrix. From 6d78a09c8197c5baa5d5bf14f3317d74d0f047c6 Mon Sep 17 00:00:00 2001 From: Baptiste Legouix Date: Mon, 17 Jun 2024 11:43:45 +0200 Subject: [PATCH 150/189] Update include/ddc/kernels/splines/splines_linear_problem_maker.hpp Co-authored-by: Thomas Padioleau --- include/ddc/kernels/splines/splines_linear_problem_maker.hpp | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_maker.hpp b/include/ddc/kernels/splines/splines_linear_problem_maker.hpp index c28250d65..cf45e8f15 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_maker.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_maker.hpp @@ -116,8 +116,10 @@ class SplinesLinearProblemMaker int const ku, bool const pds) { + assert(kl <= n); + assert(ku <= n); int const bottom_size = std::max(kl, ku); - int const top_size = std::max(0, n - bottom_size); + int const top_size = n - bottom_size; if (bottom_size * (n + top_size) + (2 * kl + ku + 1) * top_size >= n * n) { return std::make_unique>(n); From 8f6b79a6a22d4d458c9981d61db2cafa7e561648 Mon Sep 17 00:00:00 2001 From: Baptiste Legouix Date: Mon, 17 Jun 2024 11:57:08 +0200 Subject: [PATCH 151/189] Update include/ddc/kernels/splines/splines_linear_problem_maker.hpp --- include/ddc/kernels/splines/splines_linear_problem_maker.hpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_maker.hpp b/include/ddc/kernels/splines/splines_linear_problem_maker.hpp index cf45e8f15..2826f5692 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_maker.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_maker.hpp @@ -116,8 +116,8 @@ class SplinesLinearProblemMaker int const ku, bool const pds) { - assert(kl <= n); - assert(ku <= n); + assert(kl < n); + assert(ku < n); int const bottom_size = std::max(kl, ku); int const top_size = n - bottom_size; From 29a7bd12c3ef8ea1c45ee9185a827566ec5e464e Mon Sep 17 00:00:00 2001 From: blegouix Date: Mon, 17 Jun 2024 12:45:44 +0200 Subject: [PATCH 152/189] fix --- tests/splines/matrix.cpp | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/tests/splines/matrix.cpp b/tests/splines/matrix.cpp index ba0d1fe69..b3ca29f3c 100644 --- a/tests/splines/matrix.cpp +++ b/tests/splines/matrix.cpp @@ -344,7 +344,7 @@ TEST_P(MatrixSizesFixture, PeriodicBand) auto const [N, k] = GetParam(); // Build a full-rank periodic band matrix permuted in such a way the band is shifted - for (std::ptrdiff_t s(-k); s < (std::ptrdiff_t)k + 1; ++s) { + for (std::ptrdiff_t s(-k + k / 2); s < (std::ptrdiff_t)k - k / 2 + 1; ++s) { std::unique_ptr> matrix = ddc::detail::SplinesLinearProblemMaker::make_new_periodic_band_matrix< Kokkos::DefaultExecutionSpace>( @@ -357,9 +357,9 @@ TEST_P(MatrixSizesFixture, PeriodicBand) std::ptrdiff_t diag = ddc::detail::modulo((std::ptrdiff_t)(j - i), (std::ptrdiff_t)N); if (diag == s || diag == N + s) { - matrix->set_element(i, j, .5); + matrix->set_element(i, j, 2.0 * k + 1); } else if (diag <= s + k || diag >= N + s - k) { - matrix->set_element(i, j, -1. / k); + matrix->set_element(i, j, -1.); } } } From ad6dd2e29ca04b642c3bea1e89856d5a9aaa4e93 Mon Sep 17 00:00:00 2001 From: blegouix Date: Mon, 17 Jun 2024 12:51:25 +0200 Subject: [PATCH 153/189] static_cast --- tests/splines/matrix.cpp | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/tests/splines/matrix.cpp b/tests/splines/matrix.cpp index e0c8c20a0..9135a35ea 100644 --- a/tests/splines/matrix.cpp +++ b/tests/splines/matrix.cpp @@ -344,18 +344,18 @@ TEST_P(MatrixSizesFixture, PeriodicBand) auto const [N, k] = GetParam(); // Build a full-rank periodic band matrix permuted in such a way the band is shifted - for (std::ptrdiff_t s(-k + k / 2); s < (std::ptrdiff_t)k - k / 2 + 1; ++s) { + for (std::ptrdiff_t s(-k + k / 2); s < static_cast(k - k / 2 + 1); ++s) { std::unique_ptr> matrix = ddc::detail::SplinesLinearProblemMaker::make_new_periodic_band_matrix< Kokkos::DefaultExecutionSpace>( N, - (std::ptrdiff_t)k - s, - (std::ptrdiff_t)k + s, + static_cast(k - s), + k + s, false); for (std::size_t i(0); i < N; ++i) { for (std::size_t j(0); j < N; ++j) { - std::ptrdiff_t diag - = ddc::detail::modulo((std::ptrdiff_t)(j - i), (std::ptrdiff_t)N); + std::ptrdiff_t diag = ddc::detail:: + modulo(static_cast(j - i), static_cast(N)); if (diag == s || diag == N + s) { matrix->set_element(i, j, 2.0 * k + 1); } else if (diag <= s + k || diag >= N + s - k) { From 9b5fd29931a3e695c775b9ce2425a0cdf1cf19cd Mon Sep 17 00:00:00 2001 From: blegouix Date: Mon, 17 Jun 2024 13:17:56 +0200 Subject: [PATCH 154/189] fix --- tests/splines/matrix.cpp | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/tests/splines/matrix.cpp b/tests/splines/matrix.cpp index 9135a35ea..246ae4f6d 100644 --- a/tests/splines/matrix.cpp +++ b/tests/splines/matrix.cpp @@ -344,7 +344,8 @@ TEST_P(MatrixSizesFixture, PeriodicBand) auto const [N, k] = GetParam(); // Build a full-rank periodic band matrix permuted in such a way the band is shifted - for (std::ptrdiff_t s(-k + k / 2); s < static_cast(k - k / 2 + 1); ++s) { + for (std::ptrdiff_t s(-k + k / 2 + 1); s < static_cast(k - k / 2); ++s) { + std::cout << s; std::unique_ptr> matrix = ddc::detail::SplinesLinearProblemMaker::make_new_periodic_band_matrix< Kokkos::DefaultExecutionSpace>( From 4cf205d3442114e533276456ef7f9e62e62bd9c5 Mon Sep 17 00:00:00 2001 From: blegouix Date: Mon, 17 Jun 2024 13:55:01 +0200 Subject: [PATCH 155/189] fix bad merge --- include/ddc/kernels/splines.hpp | 1 - .../splines/splines_linear_problem_maker.hpp | 39 --- .../splines_linear_problem_periodic_band.hpp | 270 ------------------ 3 files changed, 310 deletions(-) delete mode 100644 include/ddc/kernels/splines/splines_linear_problem_periodic_band.hpp diff --git a/include/ddc/kernels/splines.hpp b/include/ddc/kernels/splines.hpp index 67081eff4..27595fecd 100644 --- a/include/ddc/kernels/splines.hpp +++ b/include/ddc/kernels/splines.hpp @@ -26,6 +26,5 @@ #include "splines/splines_linear_problem_maker.hpp" #include "splines/splines_linear_problem_pds_band.hpp" #include "splines/splines_linear_problem_pds_tridiag.hpp" -#include "splines/splines_linear_problem_periodic_band.hpp" #include "splines/splines_linear_problem_sparse.hpp" #include "splines/view.hpp" diff --git a/include/ddc/kernels/splines/splines_linear_problem_maker.hpp b/include/ddc/kernels/splines/splines_linear_problem_maker.hpp index 9f0524c61..8fe8183d5 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_maker.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_maker.hpp @@ -13,7 +13,6 @@ #include "splines_linear_problem_dense.hpp" #include "splines_linear_problem_pds_band.hpp" #include "splines_linear_problem_pds_tridiag.hpp" -#include "splines_linear_problem_periodic_band.hpp" #include "splines_linear_problem_sparse.hpp" namespace ddc::detail { @@ -136,44 +135,6 @@ class SplinesLinearProblemMaker return make_new_block_matrix_with_band_main_block(n, kl, ku, pds, bottom_size); } - /** - * @brief Construct a 2x2-blocks linear problem with band "main" block (the one called - * Q in SplinesLinearProblem2x2Blocks). - * - * @tparam the Kokkos::ExecutionSpace on which matrix-related operation will be performed. - * @param n The size of one of the dimensions of the whole square matrix. - * @param kl The number of subdiagonals in the band block. - * @param ku The number of superdiagonals in the band block. - * @param pds A boolean indicating if the band block is positive-definite symetric or not. - * @param bottom_right_size The size of one of the dimensions of the bottom-right block. - * - * @return The SplinesLinearProblem instance. - */ - template - static std::unique_ptr> make_new_periodic_band_matrix( - int const n, - int const kl, - int const ku, - bool const pds) - { - int const bottom_size = std::max(kl, ku); - int const top_size = n - bottom_size; - std::unique_ptr> top_left_block; - if (bottom_size * n + bottom_size * (bottom_size + 1) + (2 * kl + 1 + ku) * top_size - >= n * n) { - return std::make_unique>(n); - } else if (pds && kl == ku && kl == 1) { - top_left_block = std::make_unique>(top_size); - } else if (kl == ku && pds) { - top_left_block = std::make_unique>(top_size, kl); - } else { - top_left_block - = std::make_unique>(top_size, kl, ku); - } - return std::make_unique< - SplinesLinearProblemPeriodicBand>(n, kl, ku, std::move(top_left_block)); - } - /** * @brief Construct a sparse matrix * diff --git a/include/ddc/kernels/splines/splines_linear_problem_periodic_band.hpp b/include/ddc/kernels/splines/splines_linear_problem_periodic_band.hpp deleted file mode 100644 index b92418813..000000000 --- a/include/ddc/kernels/splines/splines_linear_problem_periodic_band.hpp +++ /dev/null @@ -1,270 +0,0 @@ -// Copyright (C) The DDC development team, see COPYRIGHT.md file -// -// SPDX-License-Identifier: MIT - -#pragma once - -#include -#include -#include - -#include - -#include "splines_linear_problem.hpp" -#include "splines_linear_problem_dense.hpp" - -namespace ddc::detail { - -/** - * @brief A periodic-band linear problem dedicated to the computation of a spline approximation (taking in account boundary conditions), - * with all blocks except top-left one being stored in dense format. - * - * A = | Q | gamma | - * | lambda | delta | - * - * The storage format is dense row-major for top-left, top-right and bottom-left blocks, and determined by - * its type for the top-left block. - * - * This class implements a Schur complement method to perform a block-LU factorization and solve, - * calling top-left block and bottom-right block setup_solver() and solve() methods for internal operations. - * - * @tparam ExecSpace The Kokkos::ExecutionSpace on which operations related to the matrix are supposed to be performed. - */ -template -class SplinesLinearProblemPeriodicBand : public SplinesLinearProblem2x2Blocks -{ -public: - using typename SplinesLinearProblem2x2Blocks::MultiRHS; - using SplinesLinearProblem2x2Blocks::size; - -protected: - std::size_t m_kl; // no. of subdiagonals - std::size_t m_ku; // no. of superdiagonals - using SplinesLinearProblem2x2Blocks::m_top_left_block; - using SplinesLinearProblem2x2Blocks::m_top_right_block; - using SplinesLinearProblem2x2Blocks::m_bottom_left_block; - using SplinesLinearProblem2x2Blocks::m_bottom_right_block; - using SplinesLinearProblem2x2Blocks::gemv_minus1_1; - -public: - /** - * @brief SplinesLinearProblem2x2Blocks constructor. - * - * @param mat_size The size of one of the dimensions of the square matrix. - * @param q A pointer toward the top-left SplinesLinearProblem. - */ - explicit SplinesLinearProblemPeriodicBand( - std::size_t const mat_size, - std::size_t const kl, - std::size_t const ku, - std::unique_ptr> top_left_block) - : SplinesLinearProblem2x2Blocks( - mat_size, - std::move(top_left_block), - std::max(kl, ku), - std::max(kl, ku) + 1) - , m_kl(kl) - , m_ku(ku) - { - } - - double get_element(std::size_t const i, std::size_t const j) const override - { - assert(i < size()); - assert(j < size()); - - std::size_t const nq = m_top_left_block->size(); - std::size_t const ndelta = m_bottom_right_block->size(); - if (i >= nq && j < nq) { - std::ptrdiff_t d = j - i; - if (d > (std::ptrdiff_t)(size() / 2)) - d -= size(); - if (d < -(std::ptrdiff_t)(size() / 2)) - d += size(); - - if (d < -(std::ptrdiff_t)m_kl || d > (std::ptrdiff_t)m_ku) - return 0.0; - if (d > (std::ptrdiff_t)0) { - return m_bottom_left_block.h_view(i - nq, j); - } else { - return m_bottom_left_block.h_view(i - nq, j - nq + ndelta + 1); - } - } else { - return SplinesLinearProblem2x2Blocks::get_element(i, j); - } - } - - void set_element(std::size_t const i, std::size_t const j, double const aij) override - { - assert(i < size()); - assert(j < size()); - - std::size_t const nq = m_top_left_block->size(); - std::size_t const ndelta = m_bottom_right_block->size(); - if (i >= nq && j < nq) { - std::ptrdiff_t d = j - i; - if (d > (std::ptrdiff_t)(size() / 2)) - d -= size(); - if (d < -(std::ptrdiff_t)(size() / 2)) - d += size(); - - if (d < -(std::ptrdiff_t)m_kl || d > (std::ptrdiff_t)m_ku) { - assert(std::fabs(aij) < 1e-20); - return; - } - if (d > (std::ptrdiff_t)0) { - m_bottom_left_block.h_view(i - nq, j) = aij; - } else { - m_bottom_left_block.h_view(i - nq, j - nq + ndelta + 1) = aij; - } - } else { - SplinesLinearProblem2x2Blocks::set_element(i, j, aij); - } - } - -private: - // @brief Compute the Schur complement delta - lambda*Q^-1*gamma. - void compute_schur_complement() - { - Kokkos::parallel_for( - "compute_schur_complement", - Kokkos::MDRangePolicy>( - {0, 0}, - {m_bottom_right_block->size(), m_bottom_right_block->size()}), - [&](const int i, const int j) { - double val = 0.0; - // Upper diagonals in lambda, lower diagonals in gamma - for (int l = 0; l < i + 1; ++l) { - val += m_bottom_left_block.h_view(i, l) * m_top_right_block.h_view(l, j); - } - // Lower diagonals in lambda, upper diagonals in gamma - for (int l = i + 1; l < m_bottom_right_block->size() + 1; ++l) { - int const l_full - = m_top_left_block->size() - 1 - m_bottom_right_block->size() + l; - val += m_bottom_left_block.h_view(i, l) - * m_top_right_block.h_view(l_full, j); - } - m_bottom_right_block - ->set_element(i, j, m_bottom_right_block->get_element(i, j) - val); - }); - } - -public: - /** - * @brief Compute y <- y - LinOp*x or y <- y - LinOp^t*x. - * - * [SHOULD BE PRIVATE (GPU programming limitation)] - * - * @param x - * @param y - * @param LinOp - * @param transpose - */ - void per_gemv_minus1_1( - MultiRHS const x, - MultiRHS const y, - Kokkos::View const - LinOp, - bool const transpose = false) const - { - /* - assert(!transpose && LinOp.extent(0) == y.extent(0) - || transpose && LinOp.extent(1) == y.extent(0)); - assert(!transpose && LinOp.extent(1) == x.extent(0) - || transpose && LinOp.extent(0) == x.extent(0)); - */ - assert(x.extent(1) == y.extent(1)); - - std::size_t const nq = m_top_left_block->size(); - std::size_t const ndelta = m_bottom_right_block->size(); - Kokkos::parallel_for( - "per_gemv_minus1_1", - Kokkos::TeamPolicy< - ExecSpace>((y.extent(0) + transpose) * y.extent(1), Kokkos::AUTO), - KOKKOS_LAMBDA( - const typename Kokkos::TeamPolicy::member_type& teamMember) { - const int i = teamMember.league_rank() / y.extent(1); - const int j = teamMember.league_rank() % y.extent(1); - - if (!transpose) { - double LinOpTimesX = 0.; - Kokkos::parallel_reduce( - Kokkos::TeamThreadRange(teamMember, i + 1), - [&](const int l, double& LinOpTimesX_tmp) { - LinOpTimesX_tmp += LinOp(i, l) * x(l, j); - }, - LinOpTimesX); - teamMember.team_barrier(); - double LinOpTimesX2 = 0.; - Kokkos::parallel_reduce( - Kokkos::TeamThreadRange(teamMember, i + 1, ndelta), - [&](const int l, double& LinOpTimesX_tmp) { - int const l_full = nq - 1 - ndelta + l; - LinOpTimesX_tmp += LinOp(i, l) * x(l_full, j); - }, - LinOpTimesX2); - if (teamMember.team_rank() == 0) { - y(i, j) -= LinOpTimesX + LinOpTimesX2; - } - } else { - // Lower diagonals in lambda - for (int l = 0; l < i; ++l) { - if (teamMember.team_rank() == 0) { - y(nq - 1 - ndelta + i, j) -= LinOp(l, i) * x(l, j); - } - } - /// Upper diagonals in lambda - for (int l = i; l < ndelta; ++l) { - if (teamMember.team_rank() == 0) { - y(i, j) -= LinOp(l, i) * x(l, j); - } - } - } - }); - } - - /** - * @brief Solve the multiple right-hand sides linear problem Ax=b or its transposed version A^tx=b inplace. - * - * The solver method is the one known as Schur complement method. It can be summarized as follow, - * starting with the pre-computed elements of the matrix: - * - * | Q | Q^-1*gamma | - * | lambda | delta - lambda*Q^-1*gamma | - * - * For the non-transposed case: - * - Solve inplace Q * x'1 = b1 (using the solver internal to Q). - * - Compute inplace b'2 = b2 - lambda*x'1. - * - Solve inplace (delta - lambda*Q^-1*gamma) * x2 = b'2. - * - Compute inplace x1 = x'1 - (delta - lambda*Q^-1*gamma)*x2. - * - * @param[in, out] b A 2D Kokkos::View storing the multiple right-hand sides of the problem and receiving the corresponding solution. - * @param transpose Choose between the direct or transposed version of the linear problem. - */ - void solve(MultiRHS b, bool const transpose) const override - { - assert(b.extent(0) == size()); - - MultiRHS b1 = Kokkos:: - subview(b, - std::pair(0, m_top_left_block->size()), - Kokkos::ALL); - MultiRHS b2 = Kokkos:: - subview(b, - std::pair(m_top_left_block->size(), b.extent(0)), - Kokkos::ALL); - if (!transpose) { - m_top_left_block->solve(b1); - per_gemv_minus1_1(b1, b2, m_bottom_left_block.d_view); - m_bottom_right_block->solve(b2); - gemv_minus1_1(b2, b1, m_top_right_block.d_view); - } else { - gemv_minus1_1(b1, b2, m_top_right_block.d_view, true); - m_bottom_right_block->solve(b2, true); - per_gemv_minus1_1(b2, b1, m_bottom_left_block.d_view, true); - m_top_left_block->solve(b1, true); - } - } -}; - -} // namespace ddc::detail From b061d93fd5a3f97b40b0d01c2d77af94d1f23d99 Mon Sep 17 00:00:00 2001 From: blegouix Date: Mon, 17 Jun 2024 13:58:29 +0200 Subject: [PATCH 156/189] fix --- tests/splines/matrix.cpp | 27 --------------------------- 1 file changed, 27 deletions(-) diff --git a/tests/splines/matrix.cpp b/tests/splines/matrix.cpp index abce83947..598f6c5b3 100644 --- a/tests/splines/matrix.cpp +++ b/tests/splines/matrix.cpp @@ -274,33 +274,6 @@ TEST(Matrix, 3x3Blocks) solve_and_validate(*matrix); } - -TEST(Matrix, PeriodicBand) -{ - std::size_t const N = 10; - std::size_t const k = 3; - std::unique_ptr> top_left_block - = std::make_unique>(N - k, k, k); - std::unique_ptr> matrix - = std::make_unique>(N, k, k, std::move(top_left_block)); - - // Build a periodic band full-rank matrix - for (std::size_t i(0); i < N; ++i) { - for (std::size_t j(0); j < N; ++j) { - std::size_t diag = std::abs((std::ptrdiff_t)j - (std::ptrdiff_t)i) % N; - if (diag == 0 || diag == N) { - matrix->set_element(i, j, 0.5); - } else if (diag <= k || diag >= N - k) { - matrix->set_element(i, j, -1.0 / k); - } - } - } - - solve_and_validate(*matrix); -} - class MatrixSizesFixture : public testing::TestWithParam> { }; From afecda9283e52bff0561d559dddaafd8431600e4 Mon Sep 17 00:00:00 2001 From: blegouix Date: Mon, 17 Jun 2024 17:19:08 +0200 Subject: [PATCH 157/189] static_cast --- include/ddc/kernels/splines/spline_builder.hpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/include/ddc/kernels/splines/spline_builder.hpp b/include/ddc/kernels/splines/spline_builder.hpp index 250a364ae..fecfcad55 100644 --- a/include/ddc/kernels/splines/spline_builder.hpp +++ b/include/ddc/kernels/splines/spline_builder.hpp @@ -703,7 +703,7 @@ void SplineBuilder< for (std::size_t s = 0; s < bsplines_type::degree() + 1; ++s) { int const j = ddc::detail:: modulo(int(jmin.uid() - m_offset + s), - (int)ddc::discrete_space().nbasis()); + static_cast(ddc::discrete_space().nbasis())); matrix->set_element(ix.uid() - start + s_nbc_xmin, j, values(s)); } }); From 4be42f29bf07f3ca7b1fbda5fdce35b0d1c05e61 Mon Sep 17 00:00:00 2001 From: blegouix Date: Mon, 17 Jun 2024 17:30:04 +0200 Subject: [PATCH 158/189] remove custom tbsv --- .../splines_linear_problem_pds_band.hpp | 33 ------------------- vendor/benchmark | 2 +- 2 files changed, 1 insertion(+), 34 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp b/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp index a62791c17..5fdcb1696 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp @@ -121,39 +121,6 @@ class SplinesLinearProblemPDSBand : public SplinesLinearProblem m_q.sync_device(); } -private: - KOKKOS_FUNCTION int tbsv( - [[maybe_unused]] char const uplo, - [[maybe_unused]] char const trans, - [[maybe_unused]] char const diag, - int const n, - int const k, - Kokkos::View const a, - [[maybe_unused]] int const lda, - Kokkos::View const x, - [[maybe_unused]] int const incx) const - { - if (trans == 'N') { - for (int j = 0; j < n; ++j) { - if (x(j) != 0) { - x(j) /= a(0, j); - for (int i = j + 1; i <= Kokkos::min(n, j + k); ++i) { - x(i) -= a(i - j, j) * x(j); - } - } - } - } else if (trans == 'T') { - for (int j = n - 1; j >= 0; --j) { - for (int i = Kokkos::min(n, j + k); i >= j + 1; --i) { - x(j) -= a(i - j, j) * x(i); - } - x(j) /= a(0, j); - } - } - return 0; - } - -public: /** * @brief Solve the multiple right-hand sides linear problem Ax=b or its transposed version A^tx=b inplace. * diff --git a/vendor/benchmark b/vendor/benchmark index 2fa4b26e5..60b16f11a 160000 --- a/vendor/benchmark +++ b/vendor/benchmark @@ -1 +1 @@ -Subproject commit 2fa4b26e5825d0b17577ae038c3b75e2d6b5418b +Subproject commit 60b16f11a30146ac825b7d99be0b9887c24b254a From bcb474d92d3f16ad3442470085ee9608113296d0 Mon Sep 17 00:00:00 2001 From: blegouix Date: Mon, 17 Jun 2024 17:33:46 +0200 Subject: [PATCH 159/189] temporarely remove warning on old static_cast --- .github/workflows/tests.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/workflows/tests.yml b/.github/workflows/tests.yml index adaebb4e0..12905873d 100644 --- a/.github/workflows/tests.yml +++ b/.github/workflows/tests.yml @@ -142,12 +142,12 @@ jobs: 'cpu-clang') export CC=clang export CXX=clang++ - DDC_CMAKE_CXX_FLAGS="-Werror=extra-semi -Werror=old-style-cast" + DDC_CMAKE_CXX_FLAGS="-Werror=extra-semi" ;; 'cpu-gcc') export CC=gcc export CXX=g++ - DDC_CMAKE_CXX_FLAGS="-Werror=extra-semi -Werror=old-style-cast" + DDC_CMAKE_CXX_FLAGS="-Werror=extra-semi" if [ 'xDebug' = 'x${{matrix.cmake_build_type}}' ] then DDC_CMAKE_CXX_FLAGS="${DDC_CMAKE_CXX_FLAGS} -fno-omit-frame-pointer -fsanitize=address" From 5699d13c9c6f5f9c83f1abef5ab76b380cc6a16e Mon Sep 17 00:00:00 2001 From: blegouix Date: Mon, 17 Jun 2024 17:39:32 +0200 Subject: [PATCH 160/189] static_cast --- tests/splines/matrix.cpp | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/tests/splines/matrix.cpp b/tests/splines/matrix.cpp index 1d6c06829..598f6c5b3 100644 --- a/tests/splines/matrix.cpp +++ b/tests/splines/matrix.cpp @@ -427,7 +427,9 @@ TEST_P(MatrixSizesFixture, Sparse) for (std::size_t j(0); j < N; ++j) { if (i == j) { matrix->set_element(i, j, 3. / 4); - } else if (std::abs((std::ptrdiff_t)(j - i)) <= (std::ptrdiff_t)k) { + } else if ( + std::abs(static_cast(j - i)) + <= static_cast(k)) { matrix->set_element(i, j, -(1. / 4) / k); } } From 4e5017d652c77cd32b141940d588dd7b4b7982c4 Mon Sep 17 00:00:00 2001 From: blegouix Date: Mon, 17 Jun 2024 17:46:50 +0200 Subject: [PATCH 161/189] remove extra-semi --- .github/workflows/tests.yml | 2 -- 1 file changed, 2 deletions(-) diff --git a/.github/workflows/tests.yml b/.github/workflows/tests.yml index 12905873d..e5a283416 100644 --- a/.github/workflows/tests.yml +++ b/.github/workflows/tests.yml @@ -142,12 +142,10 @@ jobs: 'cpu-clang') export CC=clang export CXX=clang++ - DDC_CMAKE_CXX_FLAGS="-Werror=extra-semi" ;; 'cpu-gcc') export CC=gcc export CXX=g++ - DDC_CMAKE_CXX_FLAGS="-Werror=extra-semi" if [ 'xDebug' = 'x${{matrix.cmake_build_type}}' ] then DDC_CMAKE_CXX_FLAGS="${DDC_CMAKE_CXX_FLAGS} -fno-omit-frame-pointer -fsanitize=address" From f04661822ebfbb0bf7b292cbfd72f538c3c05963 Mon Sep 17 00:00:00 2001 From: blegouix Date: Tue, 18 Jun 2024 20:34:07 +0200 Subject: [PATCH 162/189] update kk --- vendor/kokkos-kernels | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/vendor/kokkos-kernels b/vendor/kokkos-kernels index 434e56d4e..d32806deb 160000 --- a/vendor/kokkos-kernels +++ b/vendor/kokkos-kernels @@ -1 +1 @@ -Subproject commit 434e56d4e7b7f8cc3fa25b8c02f4800397d59367 +Subproject commit d32806debdbf9d4f91513f657ca2821b0c78a4f2 From 075da5a26a903a0c85abc69a2a33763e0200a128 Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 19 Jun 2024 09:50:29 +0200 Subject: [PATCH 163/189] wip on dgbtrs --- .../splines/splines_linear_problem_band.hpp | 61 ++++++++++--------- 1 file changed, 32 insertions(+), 29 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_band.hpp b/include/ddc/kernels/splines/splines_linear_problem_band.hpp index 6615ea19a..ab50f1381 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_band.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_band.hpp @@ -8,12 +8,16 @@ #include #include +#include + #if __has_include() #include #else #include #endif +#include + #include "splines_linear_problem.hpp" namespace ddc::detail { @@ -42,8 +46,8 @@ class SplinesLinearProblemBand : public SplinesLinearProblem protected: std::size_t m_kl; // no. of subdiagonals std::size_t m_ku; // no. of superdiagonals - Kokkos::View m_ipiv; // pivot indices - Kokkos::View m_q; // band matrix representation + Kokkos::DualView m_ipiv; // pivot indices + Kokkos::DualView m_q; // band matrix representation public: /** @@ -70,7 +74,7 @@ class SplinesLinearProblemBand : public SplinesLinearProblem assert(m_kl <= mat_size); assert(m_ku <= mat_size); - Kokkos::deep_copy(m_q, 0.); + Kokkos::deep_copy(m_q.h_view, 0.); } private: @@ -94,7 +98,7 @@ class SplinesLinearProblemBand : public SplinesLinearProblem max(static_cast(0), static_cast(j) - static_cast(m_ku)) && i < std::min(size(), j + m_kl + 1)) { - return m_q(band_storage_row_index(i, j), j); + return m_q.h_view(band_storage_row_index(i, j), j); } else { return 0.0; } @@ -114,7 +118,7 @@ class SplinesLinearProblemBand : public SplinesLinearProblem max(static_cast(0), static_cast(j) - static_cast(m_ku)) && i < std::min(size(), j + m_kl + 1)) { - m_q(band_storage_row_index(i, j), j) = aij; + m_q.h_view(band_storage_row_index(i, j), j) = aij; } else { assert(std::fabs(aij) < 1e-20); } @@ -133,14 +137,20 @@ class SplinesLinearProblemBand : public SplinesLinearProblem size(), m_kl, m_ku, - m_q.data(), - m_q.stride( - 0), // m_q.stride(0) if LAPACK_ROW_MAJOR, m_q.stride(1) if LAPACK_COL_MAJOR - m_ipiv.data()); + m_q.h_view.data(), + m_q.h_view.stride( + 0), // m_q.h_view.stride(0) if LAPACK_ROW_MAJOR, m_q.h_view.stride(1) if LAPACK_COL_MAJOR + m_ipiv.h_view.data()); if (info != 0) { throw std::runtime_error( "LAPACKE_dgbtrf failed with error code " + std::to_string(info)); } + + // Push on device + m_q.modify_host(); + m_q.sync_device(); + m_ipiv.modify_host(); + m_ipiv.sync_device(); } /** @@ -155,26 +165,19 @@ class SplinesLinearProblemBand : public SplinesLinearProblem { assert(b.extent(0) == size()); - auto b_host = create_mirror_view(Kokkos::DefaultHostExecutionSpace(), b); - Kokkos::deep_copy(b_host, b); - int const info = LAPACKE_dgbtrs( - LAPACK_ROW_MAJOR, - transpose ? 'T' : 'N', - b_host.extent(0), - m_kl, - m_ku, - b_host.extent(1), - m_q.data(), - m_q.stride( - 0), // m_q.stride(0) if LAPACK_ROW_MAJOR, m_q.stride(1) if LAPACK_COL_MAJOR - m_ipiv.data(), - b_host.data(), - b_host.stride(0)); - if (info != 0) { - throw std::runtime_error( - "LAPACKE_dgbtrs failed with error code " + std::to_string(info)); - } - Kokkos::deep_copy(b, b_host); + auto q_device = m_q.d_view; + auto ipiv_device = m_ipiv.d_view; + + Kokkos::RangePolicy policy(0, b.extent(1)); + Kokkos::parallel_for( + "gbtrs", + policy, + KOKKOS_CLASS_LAMBDA(const int i) { + auto sub_b = Kokkos::subview(b, Kokkos::ALL, i); + KokkosBatched::SerialGbtrs< + KokkosBatched::Trans::NoTranspose, + KokkosBatched::Algo::Gbtrs::Unblocked>::invoke(q_device, sub_b, ipiv_device, m_kl, m_ku); + }); } }; From 5fb02ffb63b5b6a59ac435b2a47179f13ca0f2ad Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 19 Jun 2024 10:14:17 +0200 Subject: [PATCH 164/189] wip on dgbtrs --- .../splines/splines_linear_problem_band.hpp | 47 ++++++++++++++----- 1 file changed, 34 insertions(+), 13 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_band.hpp b/include/ddc/kernels/splines/splines_linear_problem_band.hpp index ab50f1381..d4735719e 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_band.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_band.hpp @@ -46,8 +46,9 @@ class SplinesLinearProblemBand : public SplinesLinearProblem protected: std::size_t m_kl; // no. of subdiagonals std::size_t m_ku; // no. of superdiagonals + Kokkos::DualView + m_q; // band matrix representation Kokkos::DualView m_ipiv; // pivot indices - Kokkos::DualView m_q; // band matrix representation public: /** @@ -146,7 +147,12 @@ class SplinesLinearProblemBand : public SplinesLinearProblem "LAPACKE_dgbtrf failed with error code " + std::to_string(info)); } - // Push on device + // Convert 1-based index to 0-based index + for (int i = 0; i < size(); ++i) { + m_ipiv.h_view(i) -= 1; + } + + // Push on device m_q.modify_host(); m_q.sync_device(); m_ipiv.modify_host(); @@ -165,19 +171,34 @@ class SplinesLinearProblemBand : public SplinesLinearProblem { assert(b.extent(0) == size()); - auto q_device = m_q.d_view; - auto ipiv_device = m_ipiv.d_view; + auto q_device = m_q.d_view; + auto ipiv_device = m_ipiv.d_view; Kokkos::RangePolicy policy(0, b.extent(1)); - Kokkos::parallel_for( - "gbtrs", - policy, - KOKKOS_CLASS_LAMBDA(const int i) { - auto sub_b = Kokkos::subview(b, Kokkos::ALL, i); - KokkosBatched::SerialGbtrs< - KokkosBatched::Trans::NoTranspose, - KokkosBatched::Algo::Gbtrs::Unblocked>::invoke(q_device, sub_b, ipiv_device, m_kl, m_ku); - }); + + if (transpose) { + Kokkos::parallel_for( + "gbtrs", + policy, + KOKKOS_CLASS_LAMBDA(const int i) { + auto sub_b = Kokkos::subview(b, Kokkos::ALL, i); + KokkosBatched::SerialGbtrs< + KokkosBatched::Trans::Transpose, + KokkosBatched::Algo::Gbtrs::Unblocked>:: + invoke(q_device, sub_b, ipiv_device, m_kl, m_ku); + }); + } else { + Kokkos::parallel_for( + "gbtrs", + policy, + KOKKOS_CLASS_LAMBDA(const int i) { + auto sub_b = Kokkos::subview(b, Kokkos::ALL, i); + KokkosBatched::SerialGbtrs< + KokkosBatched::Trans::NoTranspose, + KokkosBatched::Algo::Gbtrs::Unblocked>:: + invoke(q_device, sub_b, ipiv_device, m_kl, m_ku); + }); + } } }; From f8a2414d6a0468d578985ad839362ef248de6cef Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 19 Jun 2024 14:12:37 +0200 Subject: [PATCH 165/189] update KK --- vendor/kokkos-kernels | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/vendor/kokkos-kernels b/vendor/kokkos-kernels index d32806deb..6a9535d82 160000 --- a/vendor/kokkos-kernels +++ b/vendor/kokkos-kernels @@ -1 +1 @@ -Subproject commit d32806debdbf9d4f91513f657ca2821b0c78a4f2 +Subproject commit 6a9535d8200054484fc4158bebb5d8673a6318cf From 0795917c311718a5a5ab0426e88eeb468cb824b7 Mon Sep 17 00:00:00 2001 From: blegouix Date: Thu, 20 Jun 2024 09:33:28 +0200 Subject: [PATCH 166/189] minor --- include/ddc/kernels/splines/splines_linear_problem_band.hpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_band.hpp b/include/ddc/kernels/splines/splines_linear_problem_band.hpp index d4735719e..819185d7b 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_band.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_band.hpp @@ -65,12 +65,12 @@ class SplinesLinearProblemBand : public SplinesLinearProblem : SplinesLinearProblem(mat_size) , m_kl(kl) , m_ku(ku) - , m_ipiv("ipiv", mat_size) /* * The matrix itself stored in band format requires a (kl + ku + 1)*mat_size * allocation, but the LU-factorization requires an additional kl*mat_size block */ , m_q("q", 2 * kl + ku + 1, mat_size) + , m_ipiv("ipiv", mat_size) { assert(m_kl <= mat_size); assert(m_ku <= mat_size); From 176719dfe69dbda52250eaeb6f6b6200570fe85b Mon Sep 17 00:00:00 2001 From: Thomas Padioleau Date: Tue, 25 Jun 2024 22:10:24 +0200 Subject: [PATCH 167/189] Pre install kokkos kernels and restore flags --- .github/workflows/tests.yml | 19 +++++++++++++++++++ CMakeLists.txt | 17 ++++++++++------- 2 files changed, 29 insertions(+), 7 deletions(-) diff --git a/.github/workflows/tests.yml b/.github/workflows/tests.yml index e5a283416..a79a4c4c6 100644 --- a/.github/workflows/tests.yml +++ b/.github/workflows/tests.yml @@ -142,10 +142,12 @@ jobs: 'cpu-clang') export CC=clang export CXX=clang++ + DDC_CMAKE_CXX_FLAGS="-Werror=extra-semi -Werror=old-style-cast" ;; 'cpu-gcc') export CC=gcc export CXX=g++ + DDC_CMAKE_CXX_FLAGS="-Werror=extra-semi -Werror=old-style-cast" if [ 'xDebug' = 'x${{matrix.cmake_build_type}}' ] then DDC_CMAKE_CXX_FLAGS="${DDC_CMAKE_CXX_FLAGS} -fno-omit-frame-pointer -fsanitize=address" @@ -156,6 +158,7 @@ jobs: export benchmark_ROOT=$PWD/opt/benchmark export GTest_ROOT=$PWD/opt/gtest export Kokkos_ROOT=$PWD/opt/kokkos + export KokkosKernels_ROOT=$PWD/opt/kokkos-kernels export mdspan_ROOT=$PWD/opt/mdspan cmake \ @@ -193,6 +196,22 @@ jobs: cmake --install build --prefix $Kokkos_ROOT rm -rf build + cmake \ + -DCMAKE_BUILD_TYPE=${{matrix.cmake_build_type}} \ + -DCMAKE_CXX_STANDARD=${{matrix.cxx_version}} \ + -DKokkosKernels_ADD_DEFAULT_ETI=OFF \ + -DKokkosKernels_ENABLE_ALL_COMPONENTS=OFF \ + -DKokkosKernels_ENABLE_COMPONENT_BLAS=ON \ + -DKokkosKernels_ENABLE_COMPONENT_BATCHED=ON \ + -DKokkosKernels_ENABLE_COMPONENT_LAPACK=OFF \ + -DKokkosKernels_ENABLE_TPL_BLAS=OFF \ + -DKokkosKernels_ENABLE_TPL_LAPACK=OFF \ + -B build \ + -S /src/vendor/kokkos-kernels + cmake --build build --parallel 2 + cmake --install build --prefix $KokkosKernels_ROOT + rm -rf build + cmake \ -DCMAKE_BUILD_TYPE=${{matrix.cmake_build_type}} \ -DCMAKE_CXX_STANDARD=${{matrix.cxx_version}} \ diff --git a/CMakeLists.txt b/CMakeLists.txt index 7e2619487..c4f93923a 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -255,13 +255,16 @@ if("${DDC_BUILD_KERNELS_SPLINES}") target_include_directories(DDC INTERFACE "${LAPACKE_INCLUDE_DIRS}") # Kokkos-kernels - set(KokkosKernels_ENABLE_ALL_COMPONENTS OFF) - set(KokkosKernels_ENABLE_COMPONENT_BLAS ON) - set(KokkosKernels_ENABLE_COMPONENT_BATCHED ON) - set(KokkosKernels_ENABLE_COMPONENT_LAPACK OFF) - set(KokkosKernels_ENABLE_TPL_BLAS ON) - set(KokkosKernels_ENABLE_TPL_LAPACK OFF) - add_subdirectory(vendor/kokkos-kernels/) + find_package(KokkosKernels) + if(NOT KokkosKernels_FOUND) + set(KokkosKernels_ENABLE_ALL_COMPONENTS OFF) + set(KokkosKernels_ENABLE_COMPONENT_BLAS ON) + set(KokkosKernels_ENABLE_COMPONENT_BATCHED ON) + set(KokkosKernels_ENABLE_COMPONENT_LAPACK OFF) + set(KokkosKernels_ENABLE_TPL_BLAS ON) + set(KokkosKernels_ENABLE_TPL_LAPACK OFF) + add_subdirectory(vendor/kokkos-kernels) + endif() target_link_libraries(DDC INTERFACE Kokkos::kokkoskernels) endif() From 1e3ce12432180ca67e3dc16622f62b500568bd91 Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 26 Jun 2024 10:16:33 +0200 Subject: [PATCH 168/189] update KK --- vendor/kokkos-kernels | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/vendor/kokkos-kernels b/vendor/kokkos-kernels index 6a9535d82..45d69eb03 160000 --- a/vendor/kokkos-kernels +++ b/vendor/kokkos-kernels @@ -1 +1 @@ -Subproject commit 6a9535d8200054484fc4158bebb5d8673a6318cf +Subproject commit 45d69eb03dd7744fd10edf6511970b4c904794a8 From 68173dde2f7ea228f26f3c9ce818be0e888c5adf Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 26 Jun 2024 11:13:55 +0200 Subject: [PATCH 169/189] update KK --- vendor/kokkos-kernels | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/vendor/kokkos-kernels b/vendor/kokkos-kernels index 45d69eb03..5c003ce1e 160000 --- a/vendor/kokkos-kernels +++ b/vendor/kokkos-kernels @@ -1 +1 @@ -Subproject commit 45d69eb03dd7744fd10edf6511970b4c904794a8 +Subproject commit 5c003ce1e1182b0d79c2e285edb677f34596020b From 4518af76253e7e038747695a9827431c8466eafa Mon Sep 17 00:00:00 2001 From: Baptiste Legouix Date: Wed, 26 Jun 2024 13:04:09 +0200 Subject: [PATCH 170/189] Update CMakeLists.txt --- CMakeLists.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index c4f93923a..2909cbfb2 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -261,7 +261,7 @@ if("${DDC_BUILD_KERNELS_SPLINES}") set(KokkosKernels_ENABLE_COMPONENT_BLAS ON) set(KokkosKernels_ENABLE_COMPONENT_BATCHED ON) set(KokkosKernels_ENABLE_COMPONENT_LAPACK OFF) - set(KokkosKernels_ENABLE_TPL_BLAS ON) + set(KokkosKernels_ENABLE_TPL_BLAS OFF) set(KokkosKernels_ENABLE_TPL_LAPACK OFF) add_subdirectory(vendor/kokkos-kernels) endif() From 46c6f5e35ae45888c9b5b638655e8b04be88c1a5 Mon Sep 17 00:00:00 2001 From: Baptiste Legouix Date: Wed, 26 Jun 2024 17:37:32 +0200 Subject: [PATCH 171/189] Apply suggestions from code review Co-authored-by: Thomas Padioleau --- .../splines/splines_linear_problem_3x3_blocks.hpp | 14 +++----------- 1 file changed, 3 insertions(+), 11 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp index 8c4d0f202..977c1f81f 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp @@ -95,12 +95,12 @@ class SplinesLinearProblem3x3Blocks : public SplinesLinearProblem2x2Blocks | b_top | -- Considered as a + * | b_center | -> | b_top | -- Considered as a * | b_bottom | | b_bottom | -- single bottom block * * @param b The multiple right-hand sides. */ - void interchange_rows_from_3_to_2_blocks_rhs(MultiRHS b) const + void interchange_rows_from_3_to_2_blocks_rhs(MultiRHS const b) const { std::size_t const nq = m_top_left_block->size(); // size of the center block @@ -110,10 +110,6 @@ class SplinesLinearProblem3x3Blocks : public SplinesLinearProblem2x2Blocks {m_top_size, m_top_size + nq}, Kokkos::ALL); - MultiRHS const b_bottom = Kokkos:: - subview(b, - std::pair {m_top_size + nq, size()}, - Kokkos::ALL); MultiRHS const b_center_dst = Kokkos::subview(b, std::pair {0, nq}, Kokkos::ALL); @@ -151,10 +147,6 @@ class SplinesLinearProblem3x3Blocks : public SplinesLinearProblem2x2Blocks {m_top_size, m_top_size + nq}, Kokkos::ALL); - MultiRHS const b_bottom = Kokkos:: - subview(b, - std::pair {m_top_size + nq, size()}, - Kokkos::ALL); MultiRHS const buffer = Kokkos::create_mirror(ExecSpace(), b_center); @@ -172,7 +164,7 @@ class SplinesLinearProblem3x3Blocks : public SplinesLinearProblem2x2Blocks Date: Wed, 26 Jun 2024 17:37:44 +0200 Subject: [PATCH 172/189] Update include/ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp Co-authored-by: Thomas Padioleau --- .../ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp index 977c1f81f..de8bb0e52 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp @@ -132,7 +132,7 @@ class SplinesLinearProblem3x3Blocks : public SplinesLinearProblem2x2Blockssize(); // size of the center block From 3c2da245e1b745d5dd42f326e09604f32e042ab4 Mon Sep 17 00:00:00 2001 From: Baptiste Legouix Date: Wed, 26 Jun 2024 17:38:07 +0200 Subject: [PATCH 173/189] Apply suggestions from code review Co-authored-by: Thomas Padioleau --- .../ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp index de8bb0e52..e7a7d75cc 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp @@ -159,7 +159,7 @@ class SplinesLinearProblem3x3Blocks : public SplinesLinearProblem2x2Blocks Date: Wed, 26 Jun 2024 17:38:40 +0200 Subject: [PATCH 174/189] Update include/ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp Co-authored-by: Thomas Padioleau --- .../splines/splines_linear_problem_3x3_blocks.hpp | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp index e7a7d75cc..c2bcdb621 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp @@ -65,15 +65,17 @@ class SplinesLinearProblem3x3Blocks : public SplinesLinearProblem2x2Blockssize(); // size of the center block - if (i < m_top_size) + if (i < m_top_size) { i += nq; - else if (i < m_top_size + nq) + } else if (i < m_top_size + nq) { i -= m_top_size; + } - if (j < m_top_size) + if (j < m_top_size) { j += nq; - else if (j < m_top_size + nq) + } else if (j < m_top_size + nq) { j -= m_top_size; + } } public: From c56c130009a6e0a1839f97d0acdce2eb1ea960c2 Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 26 Jun 2024 17:57:30 +0200 Subject: [PATCH 175/189] asserts to prevent overlapping allocations --- .../kernels/splines/splines_linear_problem_3x3_blocks.hpp | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/include/ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp index c2bcdb621..1dc93e99b 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_3x3_blocks.hpp @@ -106,6 +106,9 @@ class SplinesLinearProblem3x3Blocks : public SplinesLinearProblem2x2Blockssize(); // size of the center block + // prevent Kokkos::deep_copy(b_top_dst, b_top) to be a deep_copy between overlapping allocations + assert(nq >= m_top_size); + MultiRHS const b_top = Kokkos:: subview(b, std::pair {0, m_top_size}, Kokkos::ALL); MultiRHS const b_center = Kokkos:: @@ -138,6 +141,9 @@ class SplinesLinearProblem3x3Blocks : public SplinesLinearProblem2x2Blockssize(); // size of the center block + // prevent Kokkos::deep_copy(b_top, b_top_src) to be a deep_copy between overlapping allocations + assert(nq >= m_top_size); + MultiRHS const b_center_src = Kokkos::subview(b, std::pair {0, nq}, Kokkos::ALL); MultiRHS const b_top_src = Kokkos:: From 93a2b2d3644a09f5668a34a6cb38c6be9549f62f Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 26 Jun 2024 18:07:26 +0200 Subject: [PATCH 176/189] reset 2x2 file --- .../splines_linear_problem_2x2_blocks.hpp | 32 ++----------------- 1 file changed, 2 insertions(+), 30 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp index 3769c5f07..c459166fb 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp @@ -50,7 +50,7 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem * @brief SplinesLinearProblem2x2Blocks constructor. * * @param mat_size The size of one of the dimensions of the square matrix. - * @param top_left_block A pointer toward the top-left SplinesLinearProblem. `setup_solver` must not have been called on it. + * @param top_left_block A pointer toward the top-left SplinesLinearProblem. `setup_solver` must not have been called on `q`. */ explicit SplinesLinearProblem2x2Blocks( std::size_t const mat_size, @@ -74,34 +74,6 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem Kokkos::deep_copy(m_bottom_left_block.h_view, 0.); } -protected: - /** - * @brief SplinesLinearProblem2x2Blocks constructor. - * - * @param mat_size The size of one of the dimensions of the square matrix. - * @param q A pointer toward the top-left SplinesLinearProblem. - */ - explicit SplinesLinearProblem2x2Blocks( - std::size_t const mat_size, - std::unique_ptr> top_left_block, - std::size_t const lambda_size1, - std::size_t const lambda_size2) - : SplinesLinearProblem(mat_size) - , m_top_left_block(std::move(top_left_block)) - , m_top_right_block( - "top_right_block", - m_top_left_block->size(), - mat_size - m_top_left_block->size()) - , m_bottom_left_block("bottom_left_block", lambda_size1, lambda_size2) - , m_bottom_right_block( - new SplinesLinearProblemDense(mat_size - m_top_left_block->size())) - { - assert(m_top_left_block->size() <= mat_size); - - Kokkos::deep_copy(m_top_right_block.h_view, 0.); - Kokkos::deep_copy(m_bottom_left_block.h_view, 0.); - } - double get_element(std::size_t const i, std::size_t const j) const override { assert(i < size()); @@ -201,7 +173,7 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem * @param LinOp * @param transpose */ - virtual void gemv_minus1_1( + void gemv_minus1_1( MultiRHS const x, MultiRHS const y, Kokkos::View const From 20ea4696f8b4795b7aa2f1deca0fd1a0c085f6d4 Mon Sep 17 00:00:00 2001 From: Baptiste Legouix Date: Wed, 26 Jun 2024 18:58:06 +0200 Subject: [PATCH 177/189] Update include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp --- .../ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp index c459166fb..7b7461e99 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp @@ -50,7 +50,7 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem * @brief SplinesLinearProblem2x2Blocks constructor. * * @param mat_size The size of one of the dimensions of the square matrix. - * @param top_left_block A pointer toward the top-left SplinesLinearProblem. `setup_solver` must not have been called on `q`. + * @param top_left_block A pointer toward the top-left SplinesLinearProblem. `setup_solver` must not have been called on `it`. */ explicit SplinesLinearProblem2x2Blocks( std::size_t const mat_size, From e3abfe8e9264d73064b845fbfd4a755fa2a839ff Mon Sep 17 00:00:00 2001 From: Baptiste Legouix Date: Wed, 26 Jun 2024 18:58:29 +0200 Subject: [PATCH 178/189] Update include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp --- .../ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp index 7b7461e99..fe605d71d 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_2x2_blocks.hpp @@ -50,7 +50,7 @@ class SplinesLinearProblem2x2Blocks : public SplinesLinearProblem * @brief SplinesLinearProblem2x2Blocks constructor. * * @param mat_size The size of one of the dimensions of the square matrix. - * @param top_left_block A pointer toward the top-left SplinesLinearProblem. `setup_solver` must not have been called on `it`. + * @param top_left_block A pointer toward the top-left SplinesLinearProblem. `setup_solver` must not have been called on it. */ explicit SplinesLinearProblem2x2Blocks( std::size_t const mat_size, From 86484b7599b8a970a0b523598fc8982c68188c8e Mon Sep 17 00:00:00 2001 From: Baptiste Legouix Date: Wed, 26 Jun 2024 18:58:58 +0200 Subject: [PATCH 179/189] Update tests/splines/CMakeLists.txt --- tests/splines/CMakeLists.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/splines/CMakeLists.txt b/tests/splines/CMakeLists.txt index f707a22f2..54b717828 100644 --- a/tests/splines/CMakeLists.txt +++ b/tests/splines/CMakeLists.txt @@ -113,7 +113,7 @@ foreach(BC "BC_PERIODIC" "BC_GREVILLE" "BC_HERMITE") GTest::gtest DDC::DDC ) - target_compile_definitions("${test_name}" PUBLIC -DDEGREE_X=${DEGREE_X} -D${BSPLINES_TYPE} -D${BC} -DSOLVER_LAPACK) + target_compile_definitions("${test_name}" PUBLIC -DDEGREE_X=${DEGREE_X} -D${BSPLINES_TYPE} -D${BC} -DSOLVER_LAPACK) # add_test("${test_name}" "${test_name}") gtest_discover_tests("${test_name}" DISCOVERY_MODE PRE_TEST) endforeach() From 72fc3d6af05f7d33fad2785808d3c1535d810328 Mon Sep 17 00:00:00 2001 From: blegouix Date: Fri, 28 Jun 2024 11:07:56 +0200 Subject: [PATCH 180/189] restore ginkgo tests --- tests/splines/CMakeLists.txt | 4 ++-- tests/splines/batched_spline_builder.cpp | 10 ++++++++++ 2 files changed, 12 insertions(+), 2 deletions(-) diff --git a/tests/splines/CMakeLists.txt b/tests/splines/CMakeLists.txt index 54b717828..de6476f24 100644 --- a/tests/splines/CMakeLists.txt +++ b/tests/splines/CMakeLists.txt @@ -121,9 +121,9 @@ foreach(BC "BC_PERIODIC" "BC_GREVILLE" "BC_HERMITE") endforeach() # GINKGO -foreach(BC "BC_PERIODIC") +foreach(BC "BC_PERIODIC" "BC_GREVILLE" "BC_HERMITE") foreach(DEGREE_X RANGE "${SPLINES_TEST_DEGREE_MIN}" "${SPLINES_TEST_DEGREE_MAX}") - foreach(BSPLINES_TYPE "BSPLINES_TYPE_UNIFORM") + foreach(BSPLINES_TYPE "BSPLINES_TYPE_UNIFORM" "BSPLINES_TYPE_NON_UNIFORM") set(test_name "splines_tests_BATCHED_DEGREE_X_${DEGREE_X}_${BSPLINES_TYPE}_${BC}_GINKGO") add_executable("${test_name}" ../main.cpp batched_spline_builder.cpp) target_compile_features("${test_name}" PUBLIC cxx_std_17) diff --git a/tests/splines/batched_spline_builder.cpp b/tests/splines/batched_spline_builder.cpp index c2d57805e..41d968a60 100644 --- a/tests/splines/batched_spline_builder.cpp +++ b/tests/splines/batched_spline_builder.cpp @@ -434,6 +434,16 @@ static void BatchedSplineTest() #define SUFFIX(name) name##Lapack##Hermite##NonUniform #elif defined(BC_PERIODIC) && defined(BSPLINES_TYPE_UNIFORM) && defined(SOLVER_GINKGO) #define SUFFIX(name) name##Ginkgo##Periodic##Uniform +#elif defined(BC_PERIODIC) && defined(BSPLINES_TYPE_NON_UNIFORM) && defined(SOLVER_GINKGO) +#define SUFFIX(name) name##Ginkgo##Periodic##NonUniform +#elif defined(BC_GREVILLE) && defined(BSPLINES_TYPE_UNIFORM) && defined(SOLVER_GINKGO) +#define SUFFIX(name) name##Ginkgo##Greville##Uniform +#elif defined(BC_GREVILLE) && defined(BSPLINES_TYPE_NON_UNIFORM) && defined(SOLVER_GINKGO) +#define SUFFIX(name) name##Ginkgo##Greville##NonUniform +#elif defined(BC_HERMITE) && defined(BSPLINES_TYPE_UNIFORM) && defined(SOLVER_GINKGO) +#define SUFFIX(name) name##Ginkgo##Hermite##Uniform +#elif defined(BC_HERMITE) && defined(BSPLINES_TYPE_NON_UNIFORM) && defined(SOLVER_GINKGO) +#define SUFFIX(name) name##Ginkgo##Hermite##NonUniform #endif TEST(SUFFIX(BatchedSplineHost), 1DX) From a10aaceaf1d4c52dec047d68fd0719fc8699f0c3 Mon Sep 17 00:00:00 2001 From: Yuuichi Asahi Date: Fri, 28 Jun 2024 11:30:07 +0200 Subject: [PATCH 181/189] set push/pop for tools --- .../ddc/kernels/splines/splines_linear_problem_band.hpp | 8 +++++--- .../ddc/kernels/splines/splines_linear_problem_dense.hpp | 8 +++++--- .../kernels/splines/splines_linear_problem_pds_band.hpp | 5 ++++- .../splines/splines_linear_problem_pds_tridiag.hpp | 5 ++++- 4 files changed, 18 insertions(+), 8 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_band.hpp b/include/ddc/kernels/splines/splines_linear_problem_band.hpp index 819185d7b..db7939d51 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_band.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_band.hpp @@ -174,11 +174,12 @@ class SplinesLinearProblemBand : public SplinesLinearProblem auto q_device = m_q.d_view; auto ipiv_device = m_ipiv.d_view; + std::string name = "gbtrs"; Kokkos::RangePolicy policy(0, b.extent(1)); - + Kokkos::Profiling::pushRegion(name); if (transpose) { Kokkos::parallel_for( - "gbtrs", + name, policy, KOKKOS_CLASS_LAMBDA(const int i) { auto sub_b = Kokkos::subview(b, Kokkos::ALL, i); @@ -189,7 +190,7 @@ class SplinesLinearProblemBand : public SplinesLinearProblem }); } else { Kokkos::parallel_for( - "gbtrs", + name, policy, KOKKOS_CLASS_LAMBDA(const int i) { auto sub_b = Kokkos::subview(b, Kokkos::ALL, i); @@ -199,6 +200,7 @@ class SplinesLinearProblemBand : public SplinesLinearProblem invoke(q_device, sub_b, ipiv_device, m_kl, m_ku); }); } + Kokkos::Profiling::popRegion(); } }; diff --git a/include/ddc/kernels/splines/splines_linear_problem_dense.hpp b/include/ddc/kernels/splines/splines_linear_problem_dense.hpp index 504b45c2c..5301e71cd 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_dense.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_dense.hpp @@ -115,11 +115,12 @@ class SplinesLinearProblemDense : public SplinesLinearProblem auto a_device = m_a.d_view; auto ipiv_device = m_ipiv.d_view; + std::string name = "getrs"; Kokkos::RangePolicy policy(0, b.extent(1)); - + Kokkos::Profiling::pushRegion(name); if (transpose) { Kokkos::parallel_for( - "gerts", + name, policy, KOKKOS_LAMBDA(const int i) { auto sub_b = Kokkos::subview(b, Kokkos::ALL, i); @@ -130,7 +131,7 @@ class SplinesLinearProblemDense : public SplinesLinearProblem }); } else { Kokkos::parallel_for( - "gerts", + name, policy, KOKKOS_LAMBDA(const int i) { auto sub_b = Kokkos::subview(b, Kokkos::ALL, i); @@ -140,6 +141,7 @@ class SplinesLinearProblemDense : public SplinesLinearProblem invoke(a_device, ipiv_device, sub_b); }); } + Kokkos::Profiling::popRegion(); } }; diff --git a/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp b/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp index 5fdcb1696..7f1a9ff2b 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp @@ -134,9 +134,11 @@ class SplinesLinearProblemPDSBand : public SplinesLinearProblem assert(b.extent(0) == size()); auto q_device = m_q.d_view; + std::string name = "pbtrs"; Kokkos::RangePolicy policy(0, b.extent(1)); + Kokkos::Profiling::pushRegion(name); Kokkos::parallel_for( - "pbtrs", + name, policy, KOKKOS_CLASS_LAMBDA(const int i) { auto sub_b = Kokkos::subview(b, Kokkos::ALL, i); @@ -144,6 +146,7 @@ class SplinesLinearProblemPDSBand : public SplinesLinearProblem KokkosBatched::Uplo::Lower, KokkosBatched::Algo::Pbtrs::Unblocked>::invoke(q_device, sub_b); }); + Kokkos::Profiling::popRegion(); } }; diff --git a/include/ddc/kernels/splines/splines_linear_problem_pds_tridiag.hpp b/include/ddc/kernels/splines/splines_linear_problem_pds_tridiag.hpp index 0f7813c5a..a93a65c34 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_pds_tridiag.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_pds_tridiag.hpp @@ -127,15 +127,18 @@ class SplinesLinearProblemPDSTridiag : public SplinesLinearProblem auto q_device = m_q.d_view; auto d = Kokkos::subview(q_device, 0, Kokkos::ALL); auto e = Kokkos::subview(q_device, 1, Kokkos::pair(0, q_device.extent(1) - 1)); + std::string name = "pttrs"; Kokkos::RangePolicy policy(0, b.extent(1)); + Kokkos::Profiling::pushRegion(name); Kokkos::parallel_for( - "pttrs", + name, policy, KOKKOS_CLASS_LAMBDA(const int i) { auto sub_b = Kokkos::subview(b, Kokkos::ALL, i); KokkosBatched::SerialPttrs< KokkosBatched::Algo::Pttrs::Unblocked>::invoke(d, e, sub_b); }); + Kokkos::Profiling::popRegion(); } }; From c5f49b0743329ad6fb89ff1b9073c6935eb79cb4 Mon Sep 17 00:00:00 2001 From: blegouix Date: Tue, 2 Jul 2024 18:35:49 +0200 Subject: [PATCH 182/189] Revert "set push/pop for tools" This reverts commit a10aaceaf1d4c52dec047d68fd0719fc8699f0c3. --- .../ddc/kernels/splines/splines_linear_problem_band.hpp | 8 +++----- .../ddc/kernels/splines/splines_linear_problem_dense.hpp | 8 +++----- .../kernels/splines/splines_linear_problem_pds_band.hpp | 5 +---- .../splines/splines_linear_problem_pds_tridiag.hpp | 5 +---- 4 files changed, 8 insertions(+), 18 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_band.hpp b/include/ddc/kernels/splines/splines_linear_problem_band.hpp index db7939d51..819185d7b 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_band.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_band.hpp @@ -174,12 +174,11 @@ class SplinesLinearProblemBand : public SplinesLinearProblem auto q_device = m_q.d_view; auto ipiv_device = m_ipiv.d_view; - std::string name = "gbtrs"; Kokkos::RangePolicy policy(0, b.extent(1)); - Kokkos::Profiling::pushRegion(name); + if (transpose) { Kokkos::parallel_for( - name, + "gbtrs", policy, KOKKOS_CLASS_LAMBDA(const int i) { auto sub_b = Kokkos::subview(b, Kokkos::ALL, i); @@ -190,7 +189,7 @@ class SplinesLinearProblemBand : public SplinesLinearProblem }); } else { Kokkos::parallel_for( - name, + "gbtrs", policy, KOKKOS_CLASS_LAMBDA(const int i) { auto sub_b = Kokkos::subview(b, Kokkos::ALL, i); @@ -200,7 +199,6 @@ class SplinesLinearProblemBand : public SplinesLinearProblem invoke(q_device, sub_b, ipiv_device, m_kl, m_ku); }); } - Kokkos::Profiling::popRegion(); } }; diff --git a/include/ddc/kernels/splines/splines_linear_problem_dense.hpp b/include/ddc/kernels/splines/splines_linear_problem_dense.hpp index 5301e71cd..504b45c2c 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_dense.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_dense.hpp @@ -115,12 +115,11 @@ class SplinesLinearProblemDense : public SplinesLinearProblem auto a_device = m_a.d_view; auto ipiv_device = m_ipiv.d_view; - std::string name = "getrs"; Kokkos::RangePolicy policy(0, b.extent(1)); - Kokkos::Profiling::pushRegion(name); + if (transpose) { Kokkos::parallel_for( - name, + "gerts", policy, KOKKOS_LAMBDA(const int i) { auto sub_b = Kokkos::subview(b, Kokkos::ALL, i); @@ -131,7 +130,7 @@ class SplinesLinearProblemDense : public SplinesLinearProblem }); } else { Kokkos::parallel_for( - name, + "gerts", policy, KOKKOS_LAMBDA(const int i) { auto sub_b = Kokkos::subview(b, Kokkos::ALL, i); @@ -141,7 +140,6 @@ class SplinesLinearProblemDense : public SplinesLinearProblem invoke(a_device, ipiv_device, sub_b); }); } - Kokkos::Profiling::popRegion(); } }; diff --git a/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp b/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp index 7f1a9ff2b..5fdcb1696 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp @@ -134,11 +134,9 @@ class SplinesLinearProblemPDSBand : public SplinesLinearProblem assert(b.extent(0) == size()); auto q_device = m_q.d_view; - std::string name = "pbtrs"; Kokkos::RangePolicy policy(0, b.extent(1)); - Kokkos::Profiling::pushRegion(name); Kokkos::parallel_for( - name, + "pbtrs", policy, KOKKOS_CLASS_LAMBDA(const int i) { auto sub_b = Kokkos::subview(b, Kokkos::ALL, i); @@ -146,7 +144,6 @@ class SplinesLinearProblemPDSBand : public SplinesLinearProblem KokkosBatched::Uplo::Lower, KokkosBatched::Algo::Pbtrs::Unblocked>::invoke(q_device, sub_b); }); - Kokkos::Profiling::popRegion(); } }; diff --git a/include/ddc/kernels/splines/splines_linear_problem_pds_tridiag.hpp b/include/ddc/kernels/splines/splines_linear_problem_pds_tridiag.hpp index a93a65c34..0f7813c5a 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_pds_tridiag.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_pds_tridiag.hpp @@ -127,18 +127,15 @@ class SplinesLinearProblemPDSTridiag : public SplinesLinearProblem auto q_device = m_q.d_view; auto d = Kokkos::subview(q_device, 0, Kokkos::ALL); auto e = Kokkos::subview(q_device, 1, Kokkos::pair(0, q_device.extent(1) - 1)); - std::string name = "pttrs"; Kokkos::RangePolicy policy(0, b.extent(1)); - Kokkos::Profiling::pushRegion(name); Kokkos::parallel_for( - name, + "pttrs", policy, KOKKOS_CLASS_LAMBDA(const int i) { auto sub_b = Kokkos::subview(b, Kokkos::ALL, i); KokkosBatched::SerialPttrs< KokkosBatched::Algo::Pttrs::Unblocked>::invoke(d, e, sub_b); }); - Kokkos::Profiling::popRegion(); } }; From e393bf7afbb5578d66cf8f1e10de24f5794e2228 Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 3 Jul 2024 17:57:18 +0200 Subject: [PATCH 183/189] do not load KokkosKernels if already loaded --- CMakeLists.txt | 22 ++++++++++++---------- 1 file changed, 12 insertions(+), 10 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 0ebe31c08..07cc6a9f6 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -255,17 +255,19 @@ if("${DDC_BUILD_KERNELS_SPLINES}") target_include_directories(DDC INTERFACE ${LAPACKE_INCLUDE_DIRS}) # Kokkos-kernels - find_package(KokkosKernels) - if(NOT KokkosKernels_FOUND) - set(KokkosKernels_ENABLE_ALL_COMPONENTS OFF) - set(KokkosKernels_ENABLE_COMPONENT_BLAS ON) - set(KokkosKernels_ENABLE_COMPONENT_BATCHED ON) - set(KokkosKernels_ENABLE_COMPONENT_LAPACK OFF) - set(KokkosKernels_ENABLE_TPL_BLAS OFF) - set(KokkosKernels_ENABLE_TPL_LAPACK OFF) - add_subdirectory(vendor/kokkos-kernels) + if(NOT TARGET Kokkos::kokkoskernels) + find_package(KokkosKernels) + if(NOT KokkosKernels_FOUND) + set(KokkosKernels_ENABLE_ALL_COMPONENTS OFF) + set(KokkosKernels_ENABLE_COMPONENT_BLAS ON) + set(KokkosKernels_ENABLE_COMPONENT_BATCHED ON) + set(KokkosKernels_ENABLE_COMPONENT_LAPACK OFF) + set(KokkosKernels_ENABLE_TPL_BLAS OFF) + set(KokkosKernels_ENABLE_TPL_LAPACK OFF) + add_subdirectory(vendor/kokkos-kernels) + endif() + target_link_libraries(DDC INTERFACE Kokkos::kokkoskernels) endif() - target_link_libraries(DDC INTERFACE Kokkos::kokkoskernels) endif() ## The PDI wrapper From ca8661e8c7ea0b1cd54b61fe428f62d9fb23bbce Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 3 Jul 2024 18:38:12 +0200 Subject: [PATCH 184/189] fix --- CMakeLists.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 07cc6a9f6..a4ae870ff 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -266,8 +266,8 @@ if("${DDC_BUILD_KERNELS_SPLINES}") set(KokkosKernels_ENABLE_TPL_LAPACK OFF) add_subdirectory(vendor/kokkos-kernels) endif() - target_link_libraries(DDC INTERFACE Kokkos::kokkoskernels) endif() + target_link_libraries(DDC INTERFACE Kokkos::kokkoskernels) endif() ## The PDI wrapper From a2168917278c89e76471ef93252cb82a82bb94c1 Mon Sep 17 00:00:00 2001 From: Baptiste Legouix Date: Thu, 4 Jul 2024 14:51:46 +0200 Subject: [PATCH 185/189] Update include/ddc/kernels/splines/splines_linear_problem_pds_tridiag.hpp Co-authored-by: Thomas Padioleau --- .../ddc/kernels/splines/splines_linear_problem_pds_tridiag.hpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_pds_tridiag.hpp b/include/ddc/kernels/splines/splines_linear_problem_pds_tridiag.hpp index 0f7813c5a..c9342d896 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_pds_tridiag.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_pds_tridiag.hpp @@ -126,7 +126,7 @@ class SplinesLinearProblemPDSTridiag : public SplinesLinearProblem assert(b.extent(0) == size()); auto q_device = m_q.d_view; auto d = Kokkos::subview(q_device, 0, Kokkos::ALL); - auto e = Kokkos::subview(q_device, 1, Kokkos::pair(0, q_device.extent(1) - 1)); + auto e = Kokkos::subview(q_device, 1, Kokkos::pair(0, q_device.extent_int(1) - 1)); Kokkos::RangePolicy policy(0, b.extent(1)); Kokkos::parallel_for( "pttrs", From dc4f713bb7a1b562456857ad64a0425add357c32 Mon Sep 17 00:00:00 2001 From: blegouix Date: Thu, 4 Jul 2024 15:18:42 +0200 Subject: [PATCH 186/189] remove KOKKOS_CLASS_LAMBDA --- .../kernels/splines/splines_linear_problem_band.hpp | 12 ++++++------ .../splines/splines_linear_problem_pds_band.hpp | 2 +- .../splines/splines_linear_problem_pds_tridiag.hpp | 5 +++-- 3 files changed, 10 insertions(+), 9 deletions(-) diff --git a/include/ddc/kernels/splines/splines_linear_problem_band.hpp b/include/ddc/kernels/splines/splines_linear_problem_band.hpp index 819185d7b..ac97ba0e0 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_band.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_band.hpp @@ -171,32 +171,32 @@ class SplinesLinearProblemBand : public SplinesLinearProblem { assert(b.extent(0) == size()); + std::size_t kl_proxy = m_kl; + std::size_t ku_proxy = m_ku; auto q_device = m_q.d_view; auto ipiv_device = m_ipiv.d_view; - Kokkos::RangePolicy policy(0, b.extent(1)); - if (transpose) { Kokkos::parallel_for( "gbtrs", policy, - KOKKOS_CLASS_LAMBDA(const int i) { + KOKKOS_LAMBDA(const int i) { auto sub_b = Kokkos::subview(b, Kokkos::ALL, i); KokkosBatched::SerialGbtrs< KokkosBatched::Trans::Transpose, KokkosBatched::Algo::Gbtrs::Unblocked>:: - invoke(q_device, sub_b, ipiv_device, m_kl, m_ku); + invoke(q_device, sub_b, ipiv_device, kl_proxy, ku_proxy); }); } else { Kokkos::parallel_for( "gbtrs", policy, - KOKKOS_CLASS_LAMBDA(const int i) { + KOKKOS_LAMBDA(const int i) { auto sub_b = Kokkos::subview(b, Kokkos::ALL, i); KokkosBatched::SerialGbtrs< KokkosBatched::Trans::NoTranspose, KokkosBatched::Algo::Gbtrs::Unblocked>:: - invoke(q_device, sub_b, ipiv_device, m_kl, m_ku); + invoke(q_device, sub_b, ipiv_device, kl_proxy, ku_proxy); }); } } diff --git a/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp b/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp index 5fdcb1696..40b3b2b22 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_pds_band.hpp @@ -138,7 +138,7 @@ class SplinesLinearProblemPDSBand : public SplinesLinearProblem Kokkos::parallel_for( "pbtrs", policy, - KOKKOS_CLASS_LAMBDA(const int i) { + KOKKOS_LAMBDA(const int i) { auto sub_b = Kokkos::subview(b, Kokkos::ALL, i); KokkosBatched::SerialPbtrs< KokkosBatched::Uplo::Lower, diff --git a/include/ddc/kernels/splines/splines_linear_problem_pds_tridiag.hpp b/include/ddc/kernels/splines/splines_linear_problem_pds_tridiag.hpp index c9342d896..6c173df60 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_pds_tridiag.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_pds_tridiag.hpp @@ -126,12 +126,13 @@ class SplinesLinearProblemPDSTridiag : public SplinesLinearProblem assert(b.extent(0) == size()); auto q_device = m_q.d_view; auto d = Kokkos::subview(q_device, 0, Kokkos::ALL); - auto e = Kokkos::subview(q_device, 1, Kokkos::pair(0, q_device.extent_int(1) - 1)); + auto e = Kokkos:: + subview(q_device, 1, Kokkos::pair(0, q_device.extent_int(1) - 1)); Kokkos::RangePolicy policy(0, b.extent(1)); Kokkos::parallel_for( "pttrs", policy, - KOKKOS_CLASS_LAMBDA(const int i) { + KOKKOS_LAMBDA(const int i) { auto sub_b = Kokkos::subview(b, Kokkos::ALL, i); KokkosBatched::SerialPttrs< KokkosBatched::Algo::Pttrs::Unblocked>::invoke(d, e, sub_b); From 7ff91e0aab724e982fdc0f8a06c6900c8799a553 Mon Sep 17 00:00:00 2001 From: blegouix Date: Fri, 5 Jul 2024 11:47:30 +0200 Subject: [PATCH 187/189] cmake DDC_KokkosKernels_DEPENDENCY_POLICY --- CMakeLists.txt | 35 +++++++++++++++++++++++++---------- 1 file changed, 25 insertions(+), 10 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index a4ae870ff..c29495ea4 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -255,18 +255,33 @@ if("${DDC_BUILD_KERNELS_SPLINES}") target_include_directories(DDC INTERFACE ${LAPACKE_INCLUDE_DIRS}) # Kokkos-kernels - if(NOT TARGET Kokkos::kokkoskernels) - find_package(KokkosKernels) - if(NOT KokkosKernels_FOUND) - set(KokkosKernels_ENABLE_ALL_COMPONENTS OFF) - set(KokkosKernels_ENABLE_COMPONENT_BLAS ON) - set(KokkosKernels_ENABLE_COMPONENT_BATCHED ON) - set(KokkosKernels_ENABLE_COMPONENT_LAPACK OFF) - set(KokkosKernels_ENABLE_TPL_BLAS OFF) - set(KokkosKernels_ENABLE_TPL_LAPACK OFF) - add_subdirectory(vendor/kokkos-kernels) + set(DDC_KokkosKernels_DEPENDENCY_POLICY "AUTO" CACHE STRING "Policy to find the `KokkosKernels` package. Options: ${DDC_DEPENDENCY_POLICIES}") + set_property(CACHE DDC_KokkosKernels_DEPENDENCY_POLICY PROPERTY STRINGS "${DDC_DEPENDENCY_POLICIES}") + if("${DDC_KokkosKernels_DEPENDENCY_POLICY}" STREQUAL "AUTO") + if(NOT TARGET Kokkos::kokkoskernels) + find_package(KokkosKernels) + if(NOT KokkosKernels_FOUND) + set(KokkosKernels_ENABLE_ALL_COMPONENTS OFF) + set(KokkosKernels_ENABLE_COMPONENT_BLAS ON) + set(KokkosKernels_ENABLE_COMPONENT_BATCHED ON) + set(KokkosKernels_ENABLE_COMPONENT_LAPACK OFF) + set(KokkosKernels_ENABLE_TPL_BLAS OFF) + set(KokkosKernels_ENABLE_TPL_LAPACK OFF) + add_subdirectory(vendor/kokkos-kernels) + endif() endif() + elseif("${DDC_KokkosKernels_DEPENDENCY_POLICY}" STREQUAL "EMBEDDED") + set(KokkosKernels_ENABLE_ALL_COMPONENTS OFF) + set(KokkosKernels_ENABLE_COMPONENT_BLAS ON) + set(KokkosKernels_ENABLE_COMPONENT_BATCHED ON) + set(KokkosKernels_ENABLE_COMPONENT_LAPACK OFF) + set(KokkosKernels_ENABLE_TPL_BLAS OFF) + set(KokkosKernels_ENABLE_TPL_LAPACK OFF) + add_subdirectory(vendor/kokkos-kernels) + elseif("${DDC_KokkosKernels_DEPENDENCY_POLICY}" STREQUAL "INSTALLED") + find_package(KokkosKernels) endif() + target_link_libraries(DDC INTERFACE Kokkos::kokkoskernels) endif() From 7205da41a9d0fe19882cf1ae785bb962a263c332 Mon Sep 17 00:00:00 2001 From: Baptiste Legouix Date: Tue, 9 Jul 2024 16:48:27 +0200 Subject: [PATCH 188/189] Update CMakeLists.txt Co-authored-by: Thomas Padioleau --- CMakeLists.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index c29495ea4..b0fe0fc13 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -279,7 +279,7 @@ if("${DDC_BUILD_KERNELS_SPLINES}") set(KokkosKernels_ENABLE_TPL_LAPACK OFF) add_subdirectory(vendor/kokkos-kernels) elseif("${DDC_KokkosKernels_DEPENDENCY_POLICY}" STREQUAL "INSTALLED") - find_package(KokkosKernels) + find_package(KokkosKernels REQUIRED) endif() target_link_libraries(DDC INTERFACE Kokkos::kokkoskernels) From beb1ee90e0ada1171cd299fd1705441936caf9ff Mon Sep 17 00:00:00 2001 From: blegouix Date: Wed, 10 Jul 2024 15:32:09 +0200 Subject: [PATCH 189/189] support order 1 splines --- include/ddc/kernels/splines/splines_linear_problem_dense.hpp | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/include/ddc/kernels/splines/splines_linear_problem_dense.hpp b/include/ddc/kernels/splines/splines_linear_problem_dense.hpp index 504b45c2c..7ee0fa47a 100644 --- a/include/ddc/kernels/splines/splines_linear_problem_dense.hpp +++ b/include/ddc/kernels/splines/splines_linear_problem_dense.hpp @@ -112,6 +112,10 @@ class SplinesLinearProblemDense : public SplinesLinearProblem { assert(b.extent(0) == size()); + // For order 1 splines, size() can be 0 then we bypass the solver call. + if (size() == 0) + return; + auto a_device = m_a.d_view; auto ipiv_device = m_ipiv.d_view;