https://mooseframework.inl.gov
KokkosAssembly.h
Go to the documentation of this file.
1 //* This file is part of the MOOSE framework
2 //* https://www.mooseframework.org
3 //*
4 //* All rights reserved, see COPYRIGHT for full restrictions
5 //* https://github.com/idaholab/moose/blob/master/COPYRIGHT
6 //*
7 //* Licensed under LGPL 2.1, please see LICENSE for details
8 //* https://www.gnu.org/licenses/lgpl-2.1.html
9 
10 #pragma once
11 
12 #include "KokkosTypes.h"
13 
14 #include "MooseMesh.h"
15 
16 #include "libmesh/elem_range.h"
17 #include "libmesh/fe_base.h"
18 #include "libmesh/fe_type.h"
19 
20 class FEProblemBase;
21 
22 namespace Moose::Kokkos
23 {
24 
28 class Assembly : public MeshHolder
29 {
30 public:
35  Assembly(FEProblemBase & problem);
39  void init();
40 
41 #ifdef MOOSE_KOKKOS_SCOPE
42 
47  unsigned int getFETypeID(FEType type) const { return libmesh_map_find(_fe_type_map, type); }
52  KOKKOS_FUNCTION unsigned int getDimension() const { return _dimension; }
57  KOKKOS_FUNCTION unsigned int getMaxQpsPerElem() const { return _max_qps_per_elem; }
63  KOKKOS_FUNCTION dof_id_type getNumQps(ContiguousSubdomainID subdomain) const
64  {
65  return _n_subdomain_qps[subdomain];
66  }
72  KOKKOS_FUNCTION unsigned int getNumQps(ElementInfo info) const { return _n_qps[info.id]; }
80  KOKKOS_FUNCTION dof_id_type getNumFaceQps(ContiguousSubdomainID subdomain) const
81  {
82  return _n_subdomain_qps_face[subdomain];
83  }
90  KOKKOS_FUNCTION unsigned int getNumFaceQps(ElementInfo info, unsigned int side) const
91  {
92  return _n_qps_face(side, info.id);
93  }
100  KOKKOS_FUNCTION dof_id_type getQpOffset(ElementInfo info) const { return _qp_offset[info.id]; }
108  KOKKOS_FUNCTION dof_id_type getQpFaceOffset(ElementInfo info, unsigned int side) const
109  {
110  return _qp_offset_face(side, info.id);
111  }
118  KOKKOS_FUNCTION dof_id_type getElemFacePropertyIndex(ElementInfo info, unsigned int side) const
119  {
120  return _elem_face_property_idx(side, info.id);
121  }
128  {
129  return _n_elem_face_properties[subdomain];
130  }
137  KOKKOS_FUNCTION unsigned int getNumDofs(unsigned int elem_type, unsigned int fe_type) const
138  {
139  return _n_dofs(elem_type, fe_type);
140  }
148  KOKKOS_FUNCTION const auto &
149  getPhi(ContiguousSubdomainID subdomain, unsigned int elem_type, unsigned int fe_type) const
150  {
151  return _phi(subdomain, elem_type, fe_type);
152  }
160  KOKKOS_FUNCTION const auto &
161  getPhiFace(ContiguousSubdomainID subdomain, unsigned int elem_type, unsigned int fe_type) const
162  {
163  return _phi_face(subdomain, elem_type, fe_type);
164  }
172  KOKKOS_FUNCTION const auto &
173  getGradPhi(ContiguousSubdomainID subdomain, unsigned int elem_type, unsigned int fe_type) const
174  {
175  return _grad_phi(subdomain, elem_type, fe_type);
176  }
184  KOKKOS_FUNCTION const auto & getGradPhiFace(ContiguousSubdomainID subdomain,
185  unsigned int elem_type,
186  unsigned int fe_type) const
187  {
188  return _grad_phi_face(subdomain, elem_type, fe_type);
189  }
196  KOKKOS_FUNCTION Real33 getJacobian(ElementInfo info, unsigned int qp) const
197  {
198  return _jacobian[info.subdomain][getQpOffset(info) + qp];
199  }
206  KOKKOS_FUNCTION Real getJxW(ElementInfo info, unsigned int qp) const
207  {
208  return _jxw[info.subdomain][getQpOffset(info) + qp];
209  }
216  KOKKOS_FUNCTION Real3 getQPoint(ElementInfo info, unsigned int qp) const
217  {
218  return _xyz[info.subdomain][getQpOffset(info) + qp];
219  }
220 
227  KOKKOS_FUNCTION Real coordTransformFactor(const ContiguousSubdomainID subdomain,
228  const Real3 point) const;
237  KOKKOS_FUNCTION void computePhysicalMap(const ElementInfo info,
238  const unsigned int qp,
239  Real33 * const jacobian,
240  Real * const JxW,
241  Real3 * const q_points) const;
252  KOKKOS_FUNCTION void computePhysicalMap(const ElementInfo info,
253  const unsigned int side,
254  const unsigned int qp,
255  Real33 * const jacobian,
256  Real * const JxW,
257  Real3 * const q_points,
258  Real3 * const normal) const;
259 
263  KOKKOS_FUNCTION void operator()(const ThreadID tid) const;
264 
269  const auto & getMaterialBoundaries() const { return _material_boundaries; }
270 #endif
271 
272 private:
276  void initQuadrature();
280  void initShape();
284  void cachePhysicalMap();
285 
297  std::map<FEType, unsigned int> _fe_type_map;
298 
302  const unsigned int _dimension;
315 
324 
330 
331  unsigned int _max_qps_per_elem = 0;
332 
336 
343 
352 
362 
373 
380 
388 
392  std::set<BoundaryID> _material_boundaries;
393 };
394 
395 #ifdef MOOSE_KOKKOS_SCOPE
396 KOKKOS_FUNCTION inline Real
398 {
399  switch (_coord_type[subdomain])
400  {
401  case Moose::COORD_XYZ:
402  return 1;
403  case Moose::COORD_RZ:
405  return 2 * M_PI *
406  (point - _rz_axis[subdomain].first).cross_product(_rz_axis[subdomain].second).norm();
407  else
408  return 2 * M_PI * point(_rz_radial_coord);
410  return 4 * M_PI * point(0) * point(0);
411  default:
412  return 0;
413  }
414 }
415 
416 KOKKOS_FUNCTION inline void
418  const unsigned int qp,
419  Real33 * const jacobian,
420  Real * const JxW,
421  Real3 * const q_points) const
422 {
423  auto sid = info.subdomain;
424  auto eid = info.id;
425  auto elem_type = info.type;
426  auto num_nodes = kokkosMesh().getNumNodes(elem_type);
427 
428  auto & phi = _map_phi(sid, elem_type);
429  auto & grad_phi = _map_grad_phi(sid, elem_type);
430 
431  Real33 J;
432  Real3 xyz;
433 
434  for (unsigned int node = 0; node < num_nodes; ++node)
435  {
436  auto points = kokkosMesh().getNodePoint(kokkosMesh().getContiguousNodeID(eid, node));
437 
438  if (jacobian || JxW)
439  J += grad_phi(node, qp).cartesian_product(points);
440 
441  xyz += phi(node, qp) * points;
442  }
443 
444  if (jacobian)
445  *jacobian = J.inverse(_dimension);
446 
447  if (JxW)
448  *JxW =
449  J.determinant(_dimension) * _weights(sid, elem_type)[qp] * coordTransformFactor(sid, xyz);
450 
451  if (q_points)
452  *q_points = xyz;
453 }
454 
455 KOKKOS_FUNCTION inline void
457  const unsigned int side,
458  const unsigned int qp,
459  Real33 * const jacobian,
460  Real * const JxW,
461  Real3 * const q_points,
462  Real3 * const normal) const
463 {
464  auto sid = info.subdomain;
465  auto eid = info.id;
466  auto elem_type = info.type;
467  auto num_nodes = kokkosMesh().getNumNodes(elem_type);
468  auto num_side_nodes = kokkosMesh().getNumNodes(elem_type, side);
469 
470  auto & phi = _map_phi_face(sid, elem_type)(side);
471  auto & grad_phi = _map_grad_phi_face(sid, elem_type)(side);
472 
473  auto & normal_dx_dxi = _normal_dx_dxi(sid, elem_type)(side);
474  auto & normal_dx_deta = _normal_dx_deta(sid, elem_type)(side);
475 
476  Real33 J;
477  Real3 xyz;
478 
479  Real3 dxyz_dxi;
480  Real3 dxyz_deta;
481 
482  for (unsigned int node = 0; node < num_nodes; ++node)
483  {
484  auto points = kokkosMesh().getNodePoint(kokkosMesh().getContiguousNodeID(eid, node));
485 
486  if (jacobian)
487  J += grad_phi(node, qp).cartesian_product(points);
488 
489  if (JxW || q_points)
490  xyz += phi(node, qp) * points;
491 
492  if (normal)
493  {
494  if (_dimension < 3)
495  dxyz_dxi += normal_dx_dxi(node, qp) * points;
496  if (_dimension == 2)
497  dxyz_deta += normal_dx_deta(node, qp) * points;
498  }
499  }
500 
501  if (jacobian)
502  *jacobian = J.inverse(_dimension);
503 
504  if (q_points)
505  *q_points = xyz;
506 
507  if (JxW || (normal && _dimension > 1))
508  {
509  J = 0;
510 
511  auto & grad_psi = _map_grad_psi_face(sid, elem_type)(side);
512 
513  for (unsigned int node = 0; node < num_side_nodes; ++node)
514  {
515  auto points = kokkosMesh().getNodePoint(kokkosMesh().getContiguousNodeID(info, side, node));
516 
517  J += grad_psi(node, qp).cartesian_product(points);
518  }
519  }
520 
521  if (JxW)
522  *JxW = ::Kokkos::sqrt((J * J.transpose()).determinant(_dimension - 1)) *
523  _weights_face(sid, elem_type)[side][qp] * coordTransformFactor(sid, xyz);
524 
525  if (normal)
526  {
527  if (_dimension == 3)
528  *normal = J.row(0).cross_product(J.row(1));
529  else if (_dimension == 2)
530  *normal = J.row(0).cross_product(dxyz_dxi.cross_product(dxyz_deta));
531  else
532  *normal = side ? dxyz_dxi : -dxyz_dxi;
533 
534  *normal *= 1.0 / normal->norm();
535  }
536 }
537 #endif
538 
546 {
547 public:
552  AssemblyHolder(const Assembly & assembly) : _assembly_host(assembly), _assembly_device(assembly)
553  {
554  }
560  {
561  }
562 
563 #ifdef MOOSE_KOKKOS_SCOPE
564 
569  KOKKOS_FUNCTION const Assembly & kokkosAssembly() const
570  {
571  KOKKOS_IF_ON_HOST(return _assembly_host;)
572 
573  return _assembly_device;
574  }
575 #endif
576 
577 private:
586 };
587 
588 } // namespace Moose::Kokkos
Array2D< Array< Real > > _weights
KOKKOS_FUNCTION const auto & getPhi(ContiguousSubdomainID subdomain, unsigned int elem_type, unsigned int fe_type) const
Get the shape functions of a FE type for an element type and subdomain.
std::map< FEType, unsigned int > _fe_type_map
FE type ID map.
AssemblyHolder(const AssemblyHolder &holder)
Copy constructor.
Array2D< Array< Array2D< Real3 > > > _map_grad_psi_face
unsigned int _rz_radial_coord
Radial coordinate index in cylindrical coordinate system.
Array2D< Array< Array2D< Real > > > _map_phi_face
The Kokkos assembly class.
The Kokkos object that contains the information of an element The IDs used in Kokkos are different fr...
Definition: KokkosMesh.h:33
Assembly(FEProblemBase &problem)
Constructor.
Array2D< unsigned int > _n_qps_face
const unsigned int invalid_uint
KOKKOS_FUNCTION dof_id_type getQpOffset(ElementInfo info) const
Get the starting offset of quadrature points of an element into the global quadrature point index...
KOKKOS_FUNCTION const Assembly & kokkosAssembly() const
Get the const reference of the Kokkos assembly.
FEProblemBase & _problem
Reference of the MOOSE problem.
KOKKOS_FUNCTION unsigned int getNumQps(ElementInfo info) const
Get the number of quadrature points of an element.
MPI_Info info
Array3D< Array< Array2D< Real > > > _phi_face
Array< Array< Real > > _jxw
Array2D< dof_id_type > _qp_offset_face
KOKKOS_INLINE_FUNCTION Real33 inverse(const unsigned int dim=3) const
Definition: KokkosTypes.h:380
Array2D< Array< Array2D< Real > > > _normal_dx_deta
Array< dof_id_type > _n_subdomain_qps_face
KOKKOS_FUNCTION unsigned int getDimension() const
Get the mesh dimension.
KOKKOS_FUNCTION void operator()(const ThreadID tid) const
Kokkos function for caching physical maps on element quadrature points.
const unsigned int _dimension
Mesh dimension.
KOKKOS_FUNCTION const auto & getGradPhiFace(ContiguousSubdomainID subdomain, unsigned int elem_type, unsigned int fe_type) const
Get the gradient of face shape functions of a FE type for an element type and subdomain.
KOKKOS_FUNCTION const auto & getGradPhi(ContiguousSubdomainID subdomain, unsigned int elem_type, unsigned int fe_type) const
Get the gradient of shape functions of a FE type for an element type and subdomain.
unsigned int getFETypeID(FEType type) const
Get the FE type ID.
KOKKOS_FUNCTION unsigned int getNumDofs(unsigned int elem_type, unsigned int fe_type) const
Get the number of DOFs of a FE type for an element type.
Array2D< Array< Array< Real > > > _weights_face
The Kokkos interface that holds the host reference of the Kokkos mesh and copies it to device during ...
Definition: KokkosMesh.h:430
KOKKOS_FUNCTION Real coordTransformFactor(const ContiguousSubdomainID subdomain, const Real3 point) const
Get the coordinate transform factor for a point in a subdomain.
Array< unsigned int > _n_qps
Number of quadrature points.
Specialization of SubProblem for solving nonlinear equations plus auxiliary equations.
Array2D< unsigned int > _n_dofs
Array2D< Array2D< Real > > _map_phi
Shape functions for computing reference-to-physical maps.
KOKKOS_INLINE_FUNCTION Real norm() const
KOKKOS_FUNCTION const auto & getPhiFace(ContiguousSubdomainID subdomain, unsigned int elem_type, unsigned int fe_type) const
Get the face shape functions of a FE type for an element type and subdomain.
void cachePhysicalMap()
Cache physical maps on element quadrature points.
Array2D< Array< Array2D< Real3 > > > _map_grad_phi_face
Array< Pair< Real3, Real3 > > _rz_axis
General axisymmetric axis of each subdomain in cylindrical coordinate system.
KOKKOS_FUNCTION unsigned int getNumNodes(unsigned int elem_type) const
Get the number of nodes of an element type.
Definition: KokkosMesh.h:208
KOKKOS_FUNCTION unsigned int getMaxQpsPerElem() const
Get the maximum number of quadrature points per element in the current partition. ...
MOOSE_KOKKOS_INDEX_TYPE ThreadID
Definition: KokkosThread.h:22
Array2D< Array< Array2D< Real > > > _normal_dx_dxi
Shape functions for computing normal vectors.
Array< Array< Real33 > > _jacobian
Cached physical maps on element quadrature points.
Array2D< Array< Real3 > > _q_points
Quadrature points and weights for reference elements.
KOKKOS_INLINE_FUNCTION Real3 cross_product(const Real3 vector) const
Array3D< Array< Array2D< Real3 > > > _grad_phi_face
MooseMesh wraps a libMesh::Mesh object and enhances its capabilities by caching additional data and s...
Definition: MooseMesh.h:93
The Kokkos interface that holds the host reference of the Kokkos assembly and copies it to device dur...
Array3D< Array2D< Real > > _phi
Shape functions for reference elements.
KOKKOS_INLINE_FUNCTION Real33 transpose() const
Definition: KokkosTypes.h:413
KOKKOS_FUNCTION dof_id_type getNumFaceQps(ContiguousSubdomainID subdomain) const
Get the total number of facial quadrature points in a subdomain NOTE: This number does not represent ...
unsigned int _max_qps_per_elem
Array2D< Array< Array< Real3 > > > _q_points_face
void initQuadrature()
Initialize quadrature data.
KOKKOS_FUNCTION Real3 getNodePoint(ContiguousNodeID node) const
Get the coordinate of a node.
Definition: KokkosMesh.h:272
Array3D< Array2D< Real3 > > _grad_phi
KOKKOS_FUNCTION Real getJxW(ElementInfo info, unsigned int qp) const
Get the transformed Jacobian weight of an element quadrature point.
KOKKOS_INLINE_FUNCTION Real determinant(const unsigned int dim=3) const
Definition: KokkosTypes.h:361
KOKKOS_FUNCTION dof_id_type getElemFacePropertySize(ContiguousSubdomainID subdomain) const
Get the size of element-constant face material property data storage of a subdomain.
KOKKOS_FUNCTION const Mesh & kokkosMesh() const
Get the const reference of the Kokkos mesh.
Definition: KokkosMesh.h:452
MooseMesh & _mesh
Reference of the MOOSE mesh.
const auto & getMaterialBoundaries() const
Get the list of boundaries to cache face material properties.
DIE A HORRIBLE DEATH HERE typedef LIBMESH_DEFAULT_SCALAR_TYPE Real
KOKKOS_FUNCTION dof_id_type getQpFaceOffset(ElementInfo info, unsigned int side) const
Get the starting offset of quadrature points of a side of an element into the global quadrature point...
void initShape()
Initialize shape data.
CTSub CT_OPERATOR_BINARY CTMul CTCompareLess CTCompareGreater CTCompareEqual _arg template * sqrt(_arg)) *_arg.template D< dtag >()) CT_SIMPLE_UNARY_FUNCTION(tanh
Array2D< Array2D< Real3 > > _map_grad_phi
Array< dof_id_type > _qp_offset
Starting offset into the global quadrature point index NOTE: The global quadrature point index is sub...
KOKKOS_FUNCTION dof_id_type getNumQps(ContiguousSubdomainID subdomain) const
Get the total number of elemental quadrature points in a subdomain.
std::set< BoundaryID > _material_boundaries
Boundaries to cache face material properties.
Array< Moose::CoordinateSystemType > _coord_type
Coordinate system type of each subdomain.
Array< Array< Real3 > > _xyz
Array< dof_id_type > _n_subdomain_qps
Array2D< Array< Array2D< Real > > > _map_psi_face
KOKKOS_FUNCTION dof_id_type getElemFacePropertyIndex(ElementInfo info, unsigned int side) const
Get the index of a side of an element into the element-constant face material property data...
KOKKOS_INLINE_FUNCTION Real3 row(const unsigned int i) const
Definition: KokkosTypes.h:425
void init()
Initialize assembly.
AssemblyHolder(const Assembly &assembly)
Constructor.
const Assembly _assembly_device
Device copy of the Kokkos assembly.
Array< dof_id_type > _n_elem_face_properties
const Assembly & _assembly_host
Host reference of the Kokkos assembly.
Array2D< dof_id_type > _elem_face_property_idx
Index into the element-constant face material property data.
KOKKOS_FUNCTION Real33 getJacobian(ElementInfo info, unsigned int qp) const
Get the inverse of Jacobian matrix of an element quadrature point.
uint8_t dof_id_type
KOKKOS_FUNCTION void computePhysicalMap(const ElementInfo info, const unsigned int qp, Real33 *const jacobian, Real *const JxW, Real3 *const q_points) const
Compute physical transformation data for an element.
KOKKOS_FUNCTION unsigned int getNumFaceQps(ElementInfo info, unsigned int side) const
Get the number of quadrature points of a side of an element.
KOKKOS_FUNCTION Real3 getQPoint(ElementInfo info, unsigned int qp) const
Get the coordinate of an element quadrature point.