PICurv 0.1.0
A Parallel Particle-In-Cell Solver for Curvilinear LES
Loading...
Searching...
No Matches
Data Structures | Macros | Enumerations | Functions
statistics_target.h File Reference

Spatial target resolution for the field-statistics pipeline. More...

#include "variables.h"
#include "field_catalog.h"
Include dependency graph for statistics_target.h:
This graph shows which files directly or indirectly include this file:

Go to the source code of this file.

Data Structures

struct  SpatialTargetPlan
 Resolved iteration domain for one field on one block. More...
 

Macros

#define PICURV_STATISTICS_FLUID_THRESHOLD   0.1
 Threshold below which a cell counts as fluid for the default mask.
 

Enumerations

enum  PicurvTargetKind { PICURV_TARGET_POINTWISE = 0 }
 Spatial mapping kind. More...
 
enum  PicurvStatisticsMask { PICURV_STATISTICS_MASK_FLUID = 0 }
 Point-eligibility mask. More...
 

Functions

PetscErrorCode PicurvLayoutDimensionIsNodeLike (FieldLayout layout, PetscInt dim, PetscBool *node_like)
 Reports whether a layout is node-like in one dimension.
 
PetscErrorCode SpatialTargetPlanCreate (UserCtx *user, FieldId field_id, PicurvStatisticsMask mask, SpatialTargetPlan *plan)
 Resolves the iteration domain for one field on one block.
 
PetscErrorCode SpatialTargetPlanLocalPointCount (const SpatialTargetPlan *plan, PetscInt *count)
 Counts the points this rank contributes.
 
PetscErrorCode SpatialTargetPlanGlobalPointCount (const SpatialTargetPlan *plan, MPI_Comm comm, PetscInt *count)
 Counts the points contributed across a communicator.
 
PetscBool SpatialTargetPlanMaskAllows (const SpatialTargetPlan *plan, PetscReal nvert_value)
 Reports whether a point passes the plan's mask.
 

Detailed Description

Spatial target resolution for the field-statistics pipeline.

Implements the pointwise identity mapping required by Field Statistics Phase 2 Implementation Specification section 6. The abstraction exists now with only that one mapping so later spatial bins, profiles, regions, and surfaces extend it rather than retrofit it.

The central responsibility is producing an iteration domain that excludes two distinct categories which Field Identity and Layout Catalog section 4 warns must not be conflated:

  1. PETSc/MPI halo entries created by DMDA decomposition, and
  2. solver-layout boundary, dummy, or duplicate-periodic indices, which exist even on a single MPI rank.

Nothing here resolves field identity or layout metadata itself; that comes from the typed catalog through FieldGetDescriptor.

Definition in file statistics_target.h.


Data Structure Documentation

◆ SpatialTargetPlan

struct SpatialTargetPlan

Resolved iteration domain for one field on one block.

Bounds are half-open [start, end) in DMDA index order (i, j, k) and are already intersected with this rank's owned range, so iterating them touches neither halo storage nor layout boundary/dummy/duplicate-periodic indices. An empty domain on a rank is represented by end[d] <= start[d].

Definition at line 49 of file statistics_target.h.

Collaboration diagram for SpatialTargetPlan:
[legend]
Data Fields
PicurvTargetKind kind Spatial mapping; always pointwise in Phase 2.
PicurvStatisticsMask mask Point-eligibility mask.
const FieldDescriptor * descriptor Catalog metadata for the targeted field.
PetscInt start[3] Inclusive start per dimension (i, j, k).
PetscInt end[3] Exclusive end per dimension (i, j, k).

Macro Definition Documentation

◆ PICURV_STATISTICS_FLUID_THRESHOLD

#define PICURV_STATISTICS_FLUID_THRESHOLD   0.1

Threshold below which a cell counts as fluid for the default mask.

Definition at line 29 of file statistics_target.h.

Enumeration Type Documentation

◆ PicurvTargetKind

Spatial mapping kind.

Phase 2 implements only the pointwise identity.

Enumerator
PICURV_TARGET_POINTWISE 

Definition at line 32 of file statistics_target.h.

32 {
PicurvTargetKind
Spatial mapping kind.
@ PICURV_TARGET_POINTWISE

◆ PicurvStatisticsMask

Point-eligibility mask.

Phase 2 implements only the fluid mask.

Enumerator
PICURV_STATISTICS_MASK_FLUID 

Definition at line 37 of file statistics_target.h.

37 {
PicurvStatisticsMask
Point-eligibility mask.
@ PICURV_STATISTICS_MASK_FLUID

Function Documentation

◆ PicurvLayoutDimensionIsNodeLike()

PetscErrorCode PicurvLayoutDimensionIsNodeLike ( FieldLayout  layout,
PetscInt  dim,
PetscBool *  node_like 
)

Reports whether a layout is node-like in one dimension.

Node-like dimensions carry one more physical entry than cell-like dimensions, because they sit on grid lines rather than between them. I_FACE is node-like in i and cell-like in j and k, and correspondingly for the other face families.

Parameters
[in]layoutCatalog layout.
[in]dimDimension index: 0 for i, 1 for j, 2 for k.
[out]node_likeResolved classification.
Returns
Zero on success, or PETSC_ERR_ARG_OUTOFRANGE for an invalid dimension, or PETSC_ERR_ARG_WRONGSTATE for a component-staggered layout, whose components do not share one classification.

Reports whether a layout is node-like in one dimension.

See also
PicurvLayoutDimensionIsNodeLike()

Definition at line 15 of file statistics_target.c.

16{
17 PetscFunctionBeginUser;
18 PetscCheck(node_like != NULL, PETSC_COMM_SELF, PETSC_ERR_ARG_NULL,
19 "Classification output is required.");
20 PetscCheck(dim >= 0 && dim < 3, PETSC_COMM_SELF, PETSC_ERR_ARG_OUTOFRANGE,
21 "Dimension must be 0, 1, or 2; got %" PetscInt_FMT ".", dim);
22
23 switch (layout) {
25 *node_like = PETSC_TRUE;
26 break;
28 *node_like = PETSC_FALSE;
29 break;
31 *node_like = (PetscBool)(dim == 0);
32 break;
34 *node_like = (PetscBool)(dim == 1);
35 break;
37 *node_like = (PetscBool)(dim == 2);
38 break;
40 /* x, y, and z live on I-, J-, and K-faces respectively, so no single
41 * classification describes the packed vector. */
42 SETERRQ(PETSC_COMM_SELF, PETSC_ERR_ARG_WRONGSTATE,
43 "Component-staggered layout has no single per-dimension classification.");
44 default:
45 SETERRQ(PETSC_COMM_SELF, PETSC_ERR_ARG_OUTOFRANGE,
46 "Unknown field layout %d.", (int)layout);
47 }
48 PetscFunctionReturn(0);
49}
@ FIELD_LAYOUT_K_FACE
@ FIELD_LAYOUT_I_FACE
@ FIELD_LAYOUT_CELL_CENTERED
@ FIELD_LAYOUT_COMPONENT_STAGGERED
@ FIELD_LAYOUT_NODE_CENTERED
@ FIELD_LAYOUT_J_FACE
Here is the caller graph for this function:

◆ SpatialTargetPlanCreate()

PetscErrorCode SpatialTargetPlanCreate ( UserCtx user,
FieldId  field_id,
PicurvStatisticsMask  mask,
SpatialTargetPlan plan 
)

Resolves the iteration domain for one field on one block.

Rejects component-staggered fields, whose x, y, and z components live on different face families and therefore cannot share a single pointwise domain. Phase 2 statistics request only cell-centered fields, but the plan resolves node and face layouts correctly so later phases inherit a verified contract.

Parameters
[in]userBlock context supplying the DMDA layout and periodicity.
[in]field_idCatalogued field to target.
[in]maskPoint-eligibility mask.
[out]planResolved plan.
Returns
Zero on success, or a PETSc error for a null argument, an unknown field, or an unsupported layout.

Resolves the iteration domain for one field on one block.

See also
SpatialTargetPlanCreate()

Definition at line 76 of file statistics_target.c.

78{
79 const FieldDescriptor *descriptor = NULL;
80 const DMDALocalInfo *info = NULL;
81 SimCtx *simCtx = NULL;
82 PetscInt owned_start[3];
83 PetscInt owned_end[3];
84 PetscInt global_size[3];
85 PetscBool periodic[3];
86
87 PetscFunctionBeginUser;
88 PetscCheck(user != NULL && plan != NULL, PETSC_COMM_SELF, PETSC_ERR_ARG_NULL,
89 "Block context and plan output are required.");
90 PetscCheck(mask == PICURV_STATISTICS_MASK_FLUID, PETSC_COMM_SELF, PETSC_ERR_ARG_OUTOFRANGE,
91 "Only the fluid mask is implemented.");
92 simCtx = user->simCtx;
93 PetscCheck(simCtx != NULL, PETSC_COMM_SELF, PETSC_ERR_ARG_WRONGSTATE,
94 "Block context must carry a simulation context.");
95
96 PetscCall(FieldGetDescriptor(field_id, &descriptor));
97 PetscCheck(descriptor->layout != FIELD_LAYOUT_COMPONENT_STAGGERED,
98 PETSC_COMM_SELF, PETSC_ERR_ARG_WRONGSTATE,
99 "Field '%s' is component-staggered; its components live on different face "
100 "families and cannot share one pointwise target domain.",
101 descriptor->canonical_name);
102
103 info = &user->info;
104 owned_start[0] = info->xs; owned_end[0] = info->xs + info->xm; global_size[0] = info->mx;
105 owned_start[1] = info->ys; owned_end[1] = info->ys + info->ym; global_size[1] = info->my;
106 owned_start[2] = info->zs; owned_end[2] = info->zs + info->zm; global_size[2] = info->mz;
107 /* The simCtx flags are authoritative here because they are what selects
108 * DM_BOUNDARY_PERIODIC when the DMDA is built, and therefore what decides
109 * whether the end planes are wrapped duplicates. */
110 periodic[0] = (PetscBool)(simCtx->i_periodic != 0);
111 periodic[1] = (PetscBool)(simCtx->j_periodic != 0);
112 periodic[2] = (PetscBool)(simCtx->k_periodic != 0);
113
115 plan->mask = mask;
116 plan->descriptor = descriptor;
117
118 for (PetscInt dim = 0; dim < 3; ++dim) {
119 PetscBool node_like = PETSC_FALSE;
120 PetscInt layout_lo = 0;
121 PetscInt layout_hi = 0;
122
123 PetscCall(PicurvLayoutDimensionIsNodeLike(descriptor->layout, dim, &node_like));
124 ResolveLayoutSpan(node_like, periodic[dim], global_size[dim], &layout_lo, &layout_hi);
125
126 /* Intersect the layout-valid span with this rank's owned range: the
127 * first exclusion removes solver-layout indices, the second removes
128 * PETSc halo storage. */
129 plan->start[dim] = PetscMax(owned_start[dim], layout_lo);
130 plan->end[dim] = PetscMin(owned_end[dim], layout_hi);
131 if (plan->end[dim] < plan->start[dim]) plan->end[dim] = plan->start[dim];
132 }
133 PetscFunctionReturn(0);
134}
FieldLayout layout
const char * canonical_name
PetscErrorCode FieldGetDescriptor(FieldId field_id, const FieldDescriptor **descriptor)
Return immutable metadata for a valid field identifier.
Immutable metadata for one field identity.
static void ResolveLayoutSpan(PetscBool node_like, PetscBool periodic, PetscInt size, PetscInt *lo, PetscInt *hi_exclusive)
Internal helper: resolves the layout-valid index span for one dimension.
PetscErrorCode PicurvLayoutDimensionIsNodeLike(FieldLayout layout, PetscInt dim, PetscBool *node_like)
Implementation of PicurvLayoutDimensionIsNodeLike().
PicurvTargetKind kind
Spatial mapping; always pointwise in Phase 2.
PetscInt end[3]
Exclusive end per dimension (i, j, k).
PetscInt start[3]
Inclusive start per dimension (i, j, k).
const FieldDescriptor * descriptor
Catalog metadata for the targeted field.
PicurvStatisticsMask mask
Point-eligibility mask.
SimCtx * simCtx
Back-pointer to the master simulation context.
Definition variables.h:899
PetscInt k_periodic
Definition variables.h:791
PetscInt i_periodic
Definition variables.h:791
DMDALocalInfo info
Definition variables.h:908
PetscInt j_periodic
Definition variables.h:791
The master context for the entire simulation.
Definition variables.h:695
Here is the call graph for this function:
Here is the caller graph for this function:

◆ SpatialTargetPlanLocalPointCount()

PetscErrorCode SpatialTargetPlanLocalPointCount ( const SpatialTargetPlan plan,
PetscInt *  count 
)

Counts the points this rank contributes.

Parameters
[in]planResolved plan.
[out]countLocal point count; zero for an empty domain.
Returns
Zero on success, or PETSC_ERR_ARG_NULL for a null argument.

Counts the points this rank contributes.

See also
SpatialTargetPlanLocalPointCount()

Definition at line 140 of file statistics_target.c.

141{
142 PetscInt total = 1;
143
144 PetscFunctionBeginUser;
145 PetscCheck(plan != NULL && count != NULL, PETSC_COMM_SELF, PETSC_ERR_ARG_NULL,
146 "Plan and count output are required.");
147 for (PetscInt dim = 0; dim < 3; ++dim) {
148 const PetscInt extent = plan->end[dim] - plan->start[dim];
149 if (extent <= 0) { *count = 0; PetscFunctionReturn(0); }
150 total *= extent;
151 }
152 *count = total;
153 PetscFunctionReturn(0);
154}
Here is the caller graph for this function:

◆ SpatialTargetPlanGlobalPointCount()

PetscErrorCode SpatialTargetPlanGlobalPointCount ( const SpatialTargetPlan plan,
MPI_Comm  comm,
PetscInt *  count 
)

Counts the points contributed across a communicator.

The result is decomposition independent: it depends only on the layout, global dimensions, and periodicity, never on how ranks divide the domain.

Parameters
[in]planResolved plan.
[in]commCommunicator to reduce over.
[out]countGlobal point count.
Returns
Zero on success, or PETSC_ERR_ARG_NULL for a null argument.

Counts the points contributed across a communicator.

See also
SpatialTargetPlanGlobalPointCount()

Definition at line 160 of file statistics_target.c.

161{
162 PetscInt local = 0;
163
164 PetscFunctionBeginUser;
165 PetscCheck(plan != NULL && count != NULL, PETSC_COMM_SELF, PETSC_ERR_ARG_NULL,
166 "Plan and count output are required.");
167 PetscCall(SpatialTargetPlanLocalPointCount(plan, &local));
168 PetscCallMPI(MPI_Allreduce(&local, count, 1, MPIU_INT, MPI_SUM, comm));
169 PetscFunctionReturn(0);
170}
PetscErrorCode SpatialTargetPlanLocalPointCount(const SpatialTargetPlan *plan, PetscInt *count)
Implementation of SpatialTargetPlanLocalPointCount().
Here is the call graph for this function:
Here is the caller graph for this function:

◆ SpatialTargetPlanMaskAllows()

PetscBool SpatialTargetPlanMaskAllows ( const SpatialTargetPlan plan,
PetscReal  nvert_value 
)

Reports whether a point passes the plan's mask.

Because Nvert changes when immersed bodies move, the mask is treated as potentially moving: callers accumulate a per-point valid count and weight rather than assuming a point contributes to every accepted state.

Parameters
[in]planResolved plan.
[in]nvert_valueNode-blanking value at the point.
Returns
PETSC_TRUE when the point is eligible.

Reports whether a point passes the plan's mask.

See also
SpatialTargetPlanMaskAllows()

Definition at line 176 of file statistics_target.c.

177{
178 if (plan == NULL) return PETSC_FALSE;
179 return (PetscBool)(nvert_value < PICURV_STATISTICS_FLUID_THRESHOLD);
180}
#define PICURV_STATISTICS_FLUID_THRESHOLD
Threshold below which a cell counts as fluid for the default mask.
Here is the caller graph for this function: