flow 1.3.0
Kokkos cut-cell IBM incompressible Navier-Stokes solver + pnm pore extraction
Loading...
Searching...
No Matches
face_props.hpp
Go to the documentation of this file.
1
17#ifndef PECLET_FLOW_FACE_PROPS_HPP
18#define PECLET_FLOW_FACE_PROPS_HPP
19
20#include <Kokkos_Core.hpp>
21
22#include "mac_cutcell.hpp"
23
24namespace peclet::flow {
25
26// Constant properties — the Var kernel with this accessor is the constant-mu operator (equivalence
27// check for the variable path).
29 double idiag_, beta_;
30 KOKKOS_INLINE_FUNCTION double idiag(long) const { return idiag_; }
31 KOKKOS_INLINE_FUNCTION double beta(long, long) const { return beta_; }
32};
33
34// Per-cell viscosity field (+ constant density for the time diagonal). harmonic=true uses the
35// harmonic face mean (continuous shear stress across a viscosity jump); false = arithmetic.
38 double rhoIdt; // rho / dt (constant-density momentum time term)
40 KOKKOS_INLINE_FUNCTION double idiag(long) const { return rhoIdt; }
41 KOKKOS_INLINE_FUNCTION double beta(long i, long j) const {
42 const double a = mu(i), b = mu(j);
43 if (harmonic) {
44 const double s = a + b;
45 return (s > 0.0) ? (2.0 * a * b / s) : 0.0;
46 }
47 return 0.5 * (a + b);
48 }
49};
50
51// General accessor: viscosity constant-or-field AND density constant-or-field. The time diagonal
52// for a variable density is the FACE density of the staggered velocity unknown (component stride
53// sc): idiag(i) = 0.5*(rho(i)+rho(i-sc))/dt — the arithmetic mean (mass is volume-additive), and
54// the SAME face density the variable-density projection uses, which is what makes discrete
55// hydrostatic balance exact. Flags select the constant fallbacks so a single-variable case (only mu
56// or only rho) composes.
59 bool haveMu = false;
60 double muC = 0.0;
61 bool harmMu = false;
63 bool haveRho = false;
64 double rhoIdtC = 0.0; // rho_/dt fallback
65 double idt = 0.0; // 1/dt (variable-rho path)
66 long sc = 0; // component face stride (staggered velocity placement)
67 // Viscosity placement stride: the staggered unknown u_c(i) sits on the -c face of cell i, so
68 // its control volume is centred there, not on cell i. 0 = collocated (the unknown IS the cell).
69 long msc = 0;
70 KOKKOS_INLINE_FUNCTION double idiag(long i) const {
71 return haveRho ? 0.5 * (rho(i) + rho(i - sc)) * idt : rhoIdtC;
72 }
73 // The two-point mean of mu across the cell face between i and j (arithmetic or harmonic).
74 KOKKOS_INLINE_FUNCTION double mean2(long i, long j) const {
75 const double a = mu(i), b = mu(j);
76 if (harmMu) {
77 const double s = a + b;
78 return (s > 0.0) ? (2.0 * a * b / s) : 0.0;
79 }
80 return 0.5 * (a + b);
81 }
82 // The viscosity on the control-volume face between the unknowns at i and j = i +- stride.
83 // Collocated (msc == 0): the cell face between cells i and j. Staggered: along the component
84 // axis the face between the unknowns i and i+msc is the CENTRE of cell i (and between i and
85 // i-msc the centre of cell i-msc), so mu is read there directly; across it (j = i +- s_a,
86 // a != c) the face is the cell EDGE shared by cells i, j, i-msc, j-msc -- the configured mean
87 // across the a-face (series), averaged over the two cells along c (parallel). The former
88 // mean2(i, j) placed mu half a cell towards +c for every component: an O(h) error, and in a
89 // walled direction a mirror asymmetry (bubble columns collected at the low wall).
90 KOKKOS_INLINE_FUNCTION double beta(long i, long j) const {
91 if (!haveMu)
92 return muC;
93 if (msc == 0)
94 return mean2(i, j);
95 if (j - i == msc)
96 return mu(i);
97 if (i - j == msc)
98 return mu(j);
99 return 0.5 * (mean2(i, j) + mean2(i - msc, j - msc));
100 }
101};
102
103} // namespace peclet::flow
104
105#endif // PECLET_FLOW_FACE_PROPS_HPP
flow — portable (Kokkos) cut-cell pressure-operator face openness from an SDF.
Kokkos::View< const double *, CCMem > CCConst
double beta(long i, long j) const
double idiag(long) const
double beta(long, long) const
double idiag(long i) const
double beta(long i, long j) const
double mean2(long i, long j) const