Codegen for lattice Boltzmann methods on unstructured grids
LBM can also be used with other discretization methods (e.g. FVM, or FEM) for the streaming step. The PDFs are now associated with the nodes of a triangular or quadrilateral mesh. Since the streaming step is now irregular and involves floating point calculation, for the update rule it is common to use two separate arrays. Nevertheless, I could still use lbmpy for the collision part by setting kernel_type='collide_only'
in the LBMConfig
.
Inspecting the prototype and code of generated kernels, e.g.
FUNC_PREFIX void mylbmkernel(double * RESTRICT _data_src,
int64_t const _size_src_0, int64_t const _size_src_1,
int64_t const _stride_src_0, int64_t const _stride_src_1, int64_t const _stride_src_2,
double omega)
I have inferred that lbmpy assumes the PDFs are stored in a 3-dimensional (padded) array (in 2D), with either the xyzf
or fxyz
storage layout. In Fortran notation, assuming fxyz
(SoA) storage this would be something like:
! In Fortran, the order is opposite from C
real(c_double), allocatable :: fcache(:,:,:,:)
! y,x,f,isrc/idst
For the unstructured method (FVM, FEM), however I will just use a "linear" array:
real(c_double), allocatable :: fcache( :,:,:)
! xy,f,isrc/idst
If I'm not mistaken, this would correspond to setting __size_src_1 = 1, __stride_src_1 = 0
to essentially "flatten" one dimension of the array.
Would it be possible for lbmpy to provide an option for applying the collision rule over a flat/one-dimensional index space? Does it make sense to do it in blocks with smaller buffers for density and velocity?