tud_lbm.io.analysis.stability
Stability diagnostics for the lax.scan time loop.
Enabled via the --debug-stability CLI flag, which sets
DEBUG_FLAG_STABILITY in tud_lbm.config.config_overview.
Every save_interval steps the runner samples a small vector of
on-device metrics and ships it to a host callback:
max|u|— maximum velocity magnitudemax|grad mu|— maximum chemical-potential gradient magnitude, derived from the stored interaction force (grad mu = -F_int / rho)min rho/max rho— density rangecheckerboard amplitude — L2 norm of
rho - 3x3-smoothed rhorestricted to the droplet wake (vapor phase, interface excluded)
The host callback appends one row per sample to stability_log.csv
(flushed per write, so the curve survives a crash), prints a status
line, and raises StabilityAbortError when any metric is NaN.
Attributes
Exceptions
Raised by the stability NaN guard; aborts the scan. |
Functions
|
L2 norm of |
|
Boolean mask for the droplet wake: vapor phase, interface excluded. |
|
Compute the stability-metric vector for one state. |
|
Build a stability-diagnostics callback for a |
Module Contents
- exception tud_lbm.io.analysis.stability.StabilityAbortError[source]
Bases:
FloatingPointErrorRaised by the stability NaN guard; aborts the scan.
- tud_lbm.io.analysis.stability.checkerboard_amplitude(rho: jax.numpy.ndarray, mask: jax.numpy.ndarray) jax.numpy.ndarray[source]
L2 norm of
rhominus its 3x3 xy-uniform-smoothed version, on mask.The smoothing is a separable 3-point mean along the x and y axes (z untouched — for 2D simulations nz=1). Rolls wrap at domain edges; the wake mask excludes wall/interface layers where that matters.
- Parameters:
rho – Density field, shape
(nx, ny, nz, 1, 1).mask – Boolean mask, broadcastable to
rho.
- Returns:
Scalar checkerboard amplitude.
- tud_lbm.io.analysis.stability.wake_mask(rho: jax.numpy.ndarray, grad_rho: jax.numpy.ndarray, rho_l: float, rho_v: float, vapor_frac: float, grad_frac: float) jax.numpy.ndarray[source]
Boolean mask for the droplet wake: vapor phase, interface excluded.
Recomputed at every sample, so the region follows the droplet. A cell is in the wake when its density is close to the vapor density AND the local density gradient is flat (excluding the diffuse interface, whose steep but smooth variation would dominate the checkerboard residual).
- Parameters:
rho – Density field, shape
(nx, ny, nz, 1, 1).grad_rho – Density gradient, shape
(nx, ny, nz, 1, d).rho_l – Liquid coexistence density.
rho_v – Vapor coexistence density.
vapor_frac – Vapor threshold —
rho < rho_v + vapor_frac * (rho_l - rho_v).grad_frac – Interface exclusion —
|grad rho| < grad_frac * (rho_l - rho_v).
- Returns:
Boolean mask, shape
(nx, ny, nz, 1, 1).
- tud_lbm.io.analysis.stability.compute_stability_metrics(state: tud_lbm.pipeline.state.state.State, *, gradient_density: tud_lbm.operators.protocols.DifferentialOperator | None = None, mp: tud_lbm.operators.macroscopic.MultiphaseParams | None = None, vapor_frac: float = 0.2, grad_frac: float = 0.05) jax.numpy.ndarray[source]
Compute the stability-metric vector for one state.
max|grad mu|is derived from the stored force rather than recomputed: the multiphase step storesforce = -rho*grad(mu) + force_extwithforce_extkept separately, sograd mu = -(force - force_ext) / rho. Single-phase states (force is None) report 0.Without multiphase parameters the checkerboard mask falls back to the whole domain.
- Returns:
Flat vector
[max_u, max_grad_mu, rho_min, rho_max, checkerboard_amp, n_wake_cells].
- tud_lbm.io.analysis.stability.make_stability_callback(out_dir: str | pathlib.Path, *, gradient_density: tud_lbm.operators.protocols.DifferentialOperator | None, mp: tud_lbm.operators.macroscopic.MultiphaseParams | None, log_interval: int, vapor_frac: float, grad_frac: float) collections.abc.Callable[source]
Build a stability-diagnostics callback for a
lax.scanbody.Mirrors
make_save_callback(): interval checking runs on-device viajax.lax.condand the metric reductions live inside the true branch, so off-interval steps cost one integer compare.- Parameters:
out_dir – Directory for
stability_log.csv.gradient_density –
setup.gradient_density(Nonefor single-phase).mp –
setup.multiphase_params(Nonefor single-phase).log_interval – Steps between samples (the run’s
save_interval).vapor_frac – See
wake_mask().grad_frac – See
wake_mask().
- Returns:
do_check(state, t)— no return value; logs as a side effect and aborts the scan on NaN.