|
MFC
Exascale flow solver
|
Go to the source code of this file.
Modules | |
| module | m_particle_cloud |
| Generates particle beds by converting particle_cloud patch specifications into individual immersed boundary patches before domain reduction. Each rank runs the same deterministic placement so no MPI broadcast of particle positions is needed. | |
Functions/Subroutines | |
| impure subroutine, public | m_particle_cloud::s_generate_particle_clouds (particle_cloud_ibs, num_particle_cloud_ibs) |
| Generate all particle beds and fill particle_cloud_ibs. Called on all ranks before s_reduce_ib_patch_array. Each packing method owns and allocates its own per-cloud working array (see s_particle_cloud_lattice / s_particle_cloud_rejection_pack) and hands back only the entries that fall within this rank's IB neighborhood. Only the first num_particle_cloud_ibs of them are actually written - callers must use that count, not size(particle_cloud_ibs), since the remainder of the array is left uninitialized. | |
| subroutine | m_particle_cloud::s_particle_cloud_rejection_pack (cloud_idx, glbl_idx, cloud_ibs, num_cloud_ibs) |
| Rejection-samples particle centres into a box or hemisphere-shell region with a minimum centre-to-centre spacing. Rejection sampling needs every placed particle tracked (regardless of which rank's neighborhood it falls in) to detect overlaps deterministically, so cloud_ibs is allocated here to the cloud's full requested particle count and only pared down to this rank's neighborhood afterwards, via s_reduce_particle_cloud_ibs. Only the per-candidate geometry sampling differs between box and hemisphere shell; it is delegated to s_sample_cloud_candidate, and every other step (overlap rejection via the spatial hash, acceptance, reduction) is geometry-independent. | |
| subroutine | m_particle_cloud::s_sample_cloud_candidate (cloud_idx, seed, rx, ry, rz, reject) |
| Draws one rejection-sampling candidate centre (rx, ry, rz) for cloud_idx, advancing seed in place. For box geometry the candidate is uniform in the box and never rejected. For a hemisphere shell the candidate is uniform in the shell volume - 2D uses theta uniform on [0, pi] with the sqrt radial CDF; 3D uses uniform phi, uniform cos(polar) on [0, 1], and the cube-root radial CDF - and reject is set when it lands within one particle radius of the flat face (the plane at y_centroid in 2D, z_centroid in 3D), a hard geometric cut applied after sampling that preserves uniformity over the remaining region. | |
| subroutine | m_particle_cloud::s_particle_cloud_lattice (cloud_idx, glbl_idx, cloud_ibs, num_cloud_ibs) |
| Places particles on the optimally dense lattice for the cloud region: a triangular lattice in 2D, a face-centered cubic lattice in 3D. The lattice spacing is set by the particle density (num_particles over the region area/volume); if that spacing falls below the required centre-to-centre distance (2*radius + min_spacing), the region is too dense and the run is aborted. No two lattice sites can overlap, so unlike rejection packing each site's IB neighborhood membership (get_neighbor_bounds() must already have run) is checked as it is generated and only in-neighborhood sites are stored; cloud_ibs is therefore allocated to the neighborhood-sized cap rather than the cloud's full particle count. | |
| subroutine | m_particle_cloud::s_add_cloud_particle (cloud_idx, ib_idx, glbl_idx, geom, px, py, pz, particle_cloud_ibs) |
| Writes a single placed particle into particle_cloud_ibs at the next free slot, advancing ib_idx. The caller decides whether this particle belongs in the array (neighborhood membership, for lattice packing, or unconditionally for rejection packing - see s_particle_cloud_lattice / s_particle_cloud_rejection_pack) and supplies its already-assigned, absolute global patch id via glbl_idx - s_reduce_ib_patch_array copies gbl_patch_id as-is. Shared by all packing methods so the per-particle ib_patch_parameters setup stays in one place. | |
| subroutine | m_particle_cloud::s_get_cloud_bin (px, py, pz, min_dist, periodic_pack, xmin, ymin, zmin, nx_bins, ny_bins, nz_bins, bx, by, bz) |
| Convert a candidate particle centre to spatial-hash bin coordinates. | |
| subroutine | m_particle_cloud::s_check_cloud_particle_overlap (px, py, pz, placed, hash_head, chain_next, hash_size, min_dist, periodic_pack, xmin, ymin, zmin, length_x, length_y, length_z, nx_bins, ny_bins, nz_bins, overlaps, bx, by, bz) |
| Check whether a candidate particle centre overlaps any already-placed particle in neighbouring spatial-hash bins. Scans the 3x3(x3) bin neighborhood - O(1) average via hash lookup - and also hands back the candidate's own bin so the caller can insert it without recomputing. | |
| subroutine | m_particle_cloud::s_reduce_particle_cloud_ibs (cloud_ibs, num_cloud_ibs) |
| Compacts cloud_ibs(1:num_ibs) in place, discarding entries outside this rank's IB neighborhood (get_neighbor_bounds() must already have run) and updating num_ibs to the retained count. Used by rejection packing, which cannot filter as it places particles (see s_particle_cloud_rejection_pack), to pare its full, unfiltered placement down to this rank's neighborhood. | |
| real(wp) function | m_particle_cloud::f_xorshift (seed) |
| Xorshift PRNG. Advances seed in-place and returns a value in [0, 1). | |
| integer function | m_particle_cloud::f_bin_hash (bx, by, bz, hash_size) |
| Hash bin coordinates to a 1-indexed slot in [1, hash_size]. Uses large prime multipliers to spread bins across buckets. Hash collisions are benign: the distance check catches false neighbours. | |