8#include <kernel/assembly/asm_traits.hpp>
9#include <kernel/lafem/dense_vector.hpp>
10#include <kernel/lafem/sparse_matrix_bcsr.hpp>
11#include <kernel/lafem/dense_vector_blocked.hpp>
66 template<
typename DT_,
typename IT_,
typename SpaceV_,
typename SpaceS_,
int dim_,
int nsc_>
70 const SpaceV_& space_v,
71 const SpaceS_& space_s,
74 const DT_ gamma = DT_(1),
75 const DT_ zeta = DT_(1)
79 XASSERTM(matrix.
rows() == space_s.get_num_dofs(),
"invalid matrix dimensions");
80 XASSERTM(matrix.
columns() == space_s.get_num_dofs(),
"invalid matrix dimensions");
81 XASSERTM(convect.
size() == space_v.get_num_dofs(),
"invalid vector size");
93 typedef typename AsmTraits::DataType DataType;
96 const typename AsmTraits::TrafoType& trafo = space_s.get_trafo();
99 typename AsmTraits::TrafoEvaluator trafo_eval(trafo);
102 typename AsmTraits::TestEvaluator space_eval_s(space_s);
103 typename AsmTraits::TrialEvaluator space_eval_v(space_v);
106 typename AsmTraits::TestDofMapping dof_mapping_s(space_s);
107 typename AsmTraits::TrialDofMapping dof_mapping_v(space_v);
110 typename AsmTraits::TrafoEvalData trafo_data;
113 typename AsmTraits::TestEvalData space_data_s;
114 typename AsmTraits::TrialEvalData space_data_v;
117 typename AsmTraits::CubatureRuleType cubature_rule(Cubature::ctor_factory, cubature_factory);
120 typename MatrixType::ScatterAxpy scatter_matrix(matrix);
123 typename VectorType::GatherAxpy gather_conv(convect);
126 static constexpr int max_local_dofs_s = AsmTraits::max_local_test_dofs;
127 static constexpr int max_local_dofs_v = AsmTraits::max_local_trial_dofs;
132 LocalMatrixType local_matrix;
139 LocalVectorType local_conv_dofs;
151 for(
typename AsmTraits::CellIterator cell(trafo_eval.begin()); cell != trafo_eval.end(); ++cell)
154 trafo_eval.prepare(cell);
157 space_eval_s.prepare(trafo_eval);
158 space_eval_v.prepare(trafo_eval);
161 dof_mapping_s.prepare(cell);
162 dof_mapping_v.prepare(cell);
165 const int num_loc_dofs_s = space_eval_s.get_num_local_dofs();
166 const int num_loc_dofs_v = space_eval_v.get_num_local_dofs();
169 local_conv_dofs.format();
170 gather_conv(local_conv_dofs, dof_mapping_v);
173 local_matrix.format();
176 for(
int point(0); point < cubature_rule.get_num_points(); ++point)
179 trafo_eval(trafo_data, cubature_rule.get_point(point));
182 space_eval_s(space_data_s, trafo_data);
183 space_eval_v(space_data_v, trafo_data);
186 const DataType weight = trafo_data.jac_det * cubature_rule.get_weight(point);
191 for(
int i(0); i < num_loc_dofs_v; ++i)
193 loc_v.
axpy(space_data_v.phi[i].value, local_conv_dofs[i]);
198 for(
int i(0); i < num_loc_dofs_s; ++i)
201 for(
int j(0); j < num_loc_dofs_s; ++j)
204 local_matrix[i][j].
add_scalar_main_diag(lambda * weight * space_data_s.phi[i].value * space_data_s.phi[j].value);
210 core_eval(local_matrix[i][j], loc_grad_v, -zeta * weight * space_data_s.phi[i].value * space_data_s.phi[j].value);
218 scatter_matrix(local_matrix, dof_mapping_s, dof_mapping_s, DataType(1));
221 dof_mapping_v.finish();
222 dof_mapping_s.finish();
225 space_eval_v.finish();
226 space_eval_s.finish();
240 template<
typename DT_>
241 static void core_eval(
Tiny::Matrix<DT_, 4, 4, 4, 4>& M,
const Tiny::Matrix<DT_, 2, 2, 2, 2>& G,
const DT_ omega)
272 M(0,0) += omega * DT_(2) * G(0,0);
273 M(0,1) += omega * G(0,1);
274 M(0,2) += omega * G(0,1);
278 M(1,0) += omega * G(1,0);
279 M(1,1) += omega * (G(0,0) + G(1,1));
281 M(1,3) += omega * G(0,1);
284 M(2,0) += omega * G(1,0);
286 M(2,2) += omega * (G(0,0) + G(1,1));
287 M(2,3) += omega * (G(0,1));
291 M(3,1) += omega * G(1,0);
292 M(3,2) += omega * G(1,0);
293 M(3,3) += omega * DT_(2) * G(1,1);
304 template<
typename DT_>
305 static void core_eval(
Tiny::Matrix<DT_, 3, 3, 3, 3>& M,
const Tiny::Matrix<DT_, 2, 2, 2, 2>& G,
const DT_ omega)
337 M(0,0) += omega * DT_(2) * G(0,0);
339 M(0,2) += omega * DT_(2) * G(0,1);
343 M(1,1) += omega * DT_(2) * G(1,1);
344 M(1,2) += omega * DT_(2) * G(1,0);
347 M(2,0) += omega * G(1,0);
348 M(2,1) += omega * G(0,1);
349 M(2,2) += omega * (G(0,0) + G(1,1));
#define XASSERTM(expr, msg)
Assertion macro definition with custom message.
Common test-/trial-space assembly traits class template.
Oldroyd-B operator assembly class.
static void core_eval(Tiny::Matrix< DT_, 3, 3, 3, 3 > &M, const Tiny::Matrix< DT_, 2, 2, 2, 2 > &G, const DT_ omega)
Auxiliary evaluation function: symmetric 2D version.
static void assemble_matrix(LAFEM::SparseMatrixBCSR< DT_, IT_, nsc_, nsc_ > &matrix, const LAFEM::DenseVectorBlocked< DT_, IT_, dim_ > &convect, const SpaceV_ &space_v, const SpaceS_ &space_s, const Cubature::DynamicFactory &cubature_factory, const DT_ lambda, const DT_ gamma=DT_(1), const DT_ zeta=DT_(1))
Assembles the Oldroyd operator onto a stress matrix.
static void core_eval(Tiny::Matrix< DT_, 4, 4, 4, 4 > &M, const Tiny::Matrix< DT_, 2, 2, 2, 2 > &G, const DT_ omega)
Auxiliary evaluation function: unsymmetric 2D version.
Blocked Dense data vector class template.
Index size() const
The number of elements.
CSR based blocked sparse matrix.
Index rows() const
Retrieve matrix row count.
Index columns() const
Retrieve matrix column count.
Tiny Matrix class template.
CUDA_HOST_DEVICE Matrix & add_scalar_main_diag(DataType alpha)
Adds a value onto the matrix's main diagonal.
CUDA_HOST_DEVICE Matrix & add_outer_product(const Vector< T_, m_, snx_ > &x, const Vector< T_, n_, sny_ > &y, const DataType alpha=DataType(1))
Adds the outer product of two vectors onto the matrix.
CUDA_HOST_DEVICE void format(DataType alpha=DataType(0))
Formats the matrix.
Tiny Vector class template.
CUDA_HOST_DEVICE void format(DataType alpha=DataType(0))
Formats the vector.
CUDA_HOST_DEVICE Vector & axpy(DataType alpha, const Vector< T_, n_, snx_ > &x)
Adds another scaled vector onto this vector.
CUDA_HOST_DEVICE T_ dot(const T_ &a, const T_ &b)
Computes the dot-product of two scalars.
@ value
specifies whether the space should supply basis function values
@ grad
specifies whether the space should supply basis function gradients
@ jac_det
specifies whether the trafo should supply jacobian determinants