Computes the dynamic Smagorinsky constant (Cs) for the LES model.
Full API contract (arguments, ownership, side effects) is documented with the header declaration in include/les.h.
31{
32 PetscErrorCode ierr;
34
35 PetscFunctionBeginUser;
37
38
39
40
41
43 ierr = VecSet(user->
CS, 0.0); CHKERRQ(ierr);
46 PetscFunctionReturn(0);
47 }
48
49
50
53 ierr = VecSet(user->
CS, simCtx->
Const_CS); CHKERRQ(ierr);
55 PetscFunctionReturn(0);
56 }
57
58
59
60 DM da = user->
da, fda = user->
fda;
61 DMDALocalInfo info;
62 PetscInt i, j, k, p, q, r;
63 PetscInt xs, xe, ys, ye, zs, ze;
64 PetscInt mx, my, mz;
65 PetscInt lxs, lxe, lys, lye, lzs, lze;
66
67
68
69 Vec lSx, lSy, lSz, lS_abs;
70 Vec lLM, lMM;
71
72
73 ierr = DMDAGetLocalInfo(da, &info); CHKERRQ(ierr);
74 mx = info.mx; my = info.my; mz = info.mz;
75 xs = info.xs; xe = xs + info.xm;
76 ys = info.ys; ye = ys + info.ym;
77 zs = info.zs; ze = zs + info.zm;
78
79
80 lxs = xs; lxe = xe; lys = ys; lye = ye; lzs = zs; lze = ze;
81 if (xs==0) lxs = xs+1;
82 if (ys==0) lys = ys+1;
83 if (zs==0) lzs = zs+1;
84 if (xe==mx) lxe = xe-1;
85 if (ye==my) lye = ye-1;
86 if (ze==mz) lze = ze-1;
87
88
89 ierr = VecDuplicate(user->
lUcont, &lSx); CHKERRQ(ierr);
90 ierr = VecDuplicate(user->
lUcont, &lSy); CHKERRQ(ierr);
91 ierr = VecDuplicate(user->
lUcont, &lSz); CHKERRQ(ierr);
92 ierr = VecDuplicate(user->
lP, &lS_abs); CHKERRQ(ierr);
93 ierr = VecDuplicate(user->
lP, &lLM); CHKERRQ(ierr);
94 ierr = VecDuplicate(user->
lP, &lMM); CHKERRQ(ierr);
95 ierr = VecSet(lLM, 0.0); CHKERRQ(ierr);
96 ierr = VecSet(lMM, 0.0); CHKERRQ(ierr);
97
98
99 Cmpnts ***ucat, ***csi, ***eta, ***zet;
100 PetscReal ***nvert, ***Cs_arr, ***aj, ***S_abs_arr, ***LM_arr, ***MM_arr;
101 Cmpnts ***Sx_arr, ***Sy_arr, ***Sz_arr;
102
103 ierr = DMDAVecGetArray(fda, user->
lUcat, &ucat); CHKERRQ(ierr);
104 ierr = DMDAVecGetArrayRead(fda, user->
lCsi, (
Cmpnts***)&csi); CHKERRQ(ierr);
105 ierr = DMDAVecGetArrayRead(fda, user->
lEta, (
Cmpnts***)&eta); CHKERRQ(ierr);
106 ierr = DMDAVecGetArrayRead(fda, user->
lZet, (
Cmpnts***)&zet); CHKERRQ(ierr);
107 ierr = DMDAVecGetArrayRead(da, user->
lNvert, (PetscReal***)&nvert); CHKERRQ(ierr);
108 ierr = DMDAVecGetArrayRead(da, user->
lAj, (PetscReal***)&aj); CHKERRQ(ierr);
109 ierr = DMDAVecGetArray(da, user->
CS, &Cs_arr); CHKERRQ(ierr);
110
111 ierr = DMDAVecGetArray(fda, lSx, &Sx_arr); CHKERRQ(ierr);
112 ierr = DMDAVecGetArray(fda, lSy, &Sy_arr); CHKERRQ(ierr);
113 ierr = DMDAVecGetArray(fda, lSz, &Sz_arr); CHKERRQ(ierr);
114 ierr = DMDAVecGetArray(da, lS_abs, &S_abs_arr); CHKERRQ(ierr);
115 ierr = DMDAVecGetArray(da, lLM, &LM_arr); CHKERRQ(ierr);
116 ierr = DMDAVecGetArray(da, lMM, &MM_arr); CHKERRQ(ierr);
117
118
119 for (k=lzs; k<lze; k++)
120 for (j=lys; j<lye; j++)
121 for (i=lxs; i<lxe; i++) {
122 if( nvert[k][j][i] > 1.1) continue;
123
126
128 double Sxy = 0.5 * (dudx.
y + dvdx.
x);
129 double Sxz = 0.5 * (dudx.
z + dwdx.
x);
131 double Syz = 0.5 * (dvdx.
z + dwdx.
y);
133 double Syx = Sxy, Szx = Sxz, Szy = Syz;
134
135 S_abs_arr[k][j][i] = sqrt( 2.0 * (Sxx*Sxx + Sxy*Sxy + Sxz*Sxz +
136 Syx*Syx + Syy*Syy + Syz*Syz +
137 Szx*Szx + Szy*Szy + Szz*Szz) );
138
139
140 Sx_arr[k][j][i] = dudx;
141 Sy_arr[k][j][i] = dvdx;
142 Sz_arr[k][j][i] = dwdx;
143 }
144
145
146 for (k=lzs; k<lze; k++)
147 for (j=lys; j<lye; j++)
148 for (i=lxs; i<lxe; i++) {
149 if(nvert[k][j][i] > 1.1) {
150 LM_arr[k][j][i] = 0.0;
151 MM_arr[k][j][i] = 0.0;
152 continue;
153 }
154
155
156 double u[3][3][3], v[3][3][3], w[3][3][3];
157 double S_abs_stencil[3][3][3];
158 double S11[3][3][3], S12[3][3][3], S13[3][3][3];
159 double S22[3][3][3], S23[3][3][3], S33[3][3][3];
160 double weights[3][3][3];
161
162 for(r=-1; r<=1; r++)
163 for(q=-1; q<=1; q++)
164 for(p=-1; p<=1; p++) {
165 int R=r+1, Q=q+1, P=p+1;
166 int KK=k+r, JJ=j+q, II=i+p;
167
168 u[R][Q][P] = ucat[KK][JJ][II].
x;
169 v[R][Q][P] = ucat[KK][JJ][II].
y;
170 w[R][Q][P] = ucat[KK][JJ][II].
z;
171
172
173 S11[R][Q][P] = Sx_arr[KK][JJ][II].
x;
174 S12[R][Q][P] = 0.5 * (Sx_arr[KK][JJ][II].
y + Sy_arr[KK][JJ][II].
x);
175 S13[R][Q][P] = 0.5 * (Sx_arr[KK][JJ][II].
z + Sz_arr[KK][JJ][II].
x);
176 S22[R][Q][P] = Sy_arr[KK][JJ][II].
y;
177 S23[R][Q][P] = 0.5 * (Sy_arr[KK][JJ][II].
z + Sz_arr[KK][JJ][II].
y);
178 S33[R][Q][P] = Sz_arr[KK][JJ][II].
z;
179
180 S_abs_stencil[R][Q][P] = S_abs_arr[KK][JJ][II];
181 weights[R][Q][P] = aj[KK][JJ][II];
182 }
183
184
188
195
197
198
199 double uu[3][3][3], uv[3][3][3], uw[3][3][3], vv[3][3][3], vw[3][3][3], ww[3][3][3];
200 for(r=0; r<3; r++) for(q=0; q<3; q++) for(p=0; p<3; p++) {
201 uu[r][q][p] = u[r][q][p] * u[r][q][p];
202 uv[r][q][p] = u[r][q][p] * v[r][q][p];
203 uw[r][q][p] = u[r][q][p] * w[r][q][p];
204 vv[r][q][p] = v[r][q][p] * v[r][q][p];
205 vw[r][q][p] = v[r][q][p] * w[r][q][p];
206 ww[r][q][p] = w[r][q][p] * w[r][q][p];
207 }
214
215
216 double L11 = uu_filt - u_filt * u_filt;
217 double L12 = uv_filt - u_filt * v_filt;
218 double L13 = uw_filt - u_filt * w_filt;
219 double L22 = vv_filt - v_filt * v_filt;
220 double L23 = vw_filt - v_filt * w_filt;
221 double L33 = ww_filt - w_filt * w_filt;
222
223
224 double grid_filter_width, test_filter_width;
226 grid_filter_width = pow(1.0 / aj[k][j][i], 1.0/3.0);
227 test_filter_width = 2.0 * grid_filter_width;
228
229 double alpha = pow(test_filter_width / grid_filter_width, 2.0);
230
231 double M11 = -2.0 * grid_filter_width * grid_filter_width * (alpha * S_abs_filt * S11_filt - S_abs_filt * S11_filt);
232 double M12 = -2.0 * grid_filter_width * grid_filter_width * (alpha * S_abs_filt * S12_filt - S_abs_filt * S12_filt);
233 double M13 = -2.0 * grid_filter_width * grid_filter_width * (alpha * S_abs_filt * S13_filt - S_abs_filt * S13_filt);
234 double M22 = -2.0 * grid_filter_width * grid_filter_width * (alpha * S_abs_filt * S22_filt - S_abs_filt * S22_filt);
235 double M23 = -2.0 * grid_filter_width * grid_filter_width * (alpha * S_abs_filt * S23_filt - S_abs_filt * S23_filt);
236 double M33 = -2.0 * grid_filter_width * grid_filter_width * (alpha * S_abs_filt * S33_filt - S_abs_filt * S33_filt);
237
238
239 LM_arr[k][j][i] = L11*M11 + 2*L12*M12 + 2*L13*M13 + L22*M22 + 2*L23*M23 + L33*M33;
240 MM_arr[k][j][i] = M11*M11 + 2*M12*M12 + 2*M13*M13 + M22*M22 + 2*M23*M23 + M33*M33;
241 }
242
243
244
245
246
247
248
249
250 for (k=lzs; k<lze; k++)
251 for (j=lys; j<lye; j++)
252 for (i=lxs; i<lxe; i++) {
253 if(nvert[k][j][i] > 1.1) {
254 Cs_arr[k][j][i] = 0.0;
255 continue;
256 }
257
258 double C_sq = 0.0;
260 C_sq = LM_arr[k][j][i] / MM_arr[k][j][i];
261 }
262
263
264 double Cs_val = (C_sq > 0.0) ? sqrt(C_sq) : 0.0;
265 Cs_arr[k][j][i] = PetscMin(PetscMax(Cs_val, 0.0), simCtx->
max_cs);
266 }
267
268
269
270
271 ierr = DMDAVecRestoreArray(fda, user->
lUcat, &ucat); CHKERRQ(ierr);
272 ierr = DMDAVecRestoreArrayRead(fda, user->
lCsi, (
Cmpnts***)&csi); CHKERRQ(ierr);
273 ierr = DMDAVecRestoreArrayRead(fda, user->
lEta, (
Cmpnts***)&eta); CHKERRQ(ierr);
274 ierr = DMDAVecRestoreArrayRead(fda, user->
lZet, (
Cmpnts***)&zet); CHKERRQ(ierr);
275 ierr = DMDAVecRestoreArrayRead(da, user->
lNvert, (PetscReal***)&nvert); CHKERRQ(ierr);
276 ierr = DMDAVecRestoreArrayRead(da, user->
lAj, (PetscReal***)&aj); CHKERRQ(ierr);
277 ierr = DMDAVecRestoreArray(da, user->
CS, &Cs_arr); CHKERRQ(ierr);
278 ierr = DMDAVecRestoreArray(fda, lSx, &Sx_arr); CHKERRQ(ierr);
279 ierr = DMDAVecRestoreArray(fda, lSy, &Sy_arr); CHKERRQ(ierr);
280 ierr = DMDAVecRestoreArray(fda, lSz, &Sz_arr); CHKERRQ(ierr);
281 ierr = DMDAVecRestoreArray(da, lS_abs, &S_abs_arr); CHKERRQ(ierr);
282 ierr = DMDAVecRestoreArray(da, lLM, &LM_arr); CHKERRQ(ierr);
283 ierr = DMDAVecRestoreArray(da, lMM, &MM_arr); CHKERRQ(ierr);
284
285
286 ierr = VecDestroy(&lSx); CHKERRQ(ierr);
287 ierr = VecDestroy(&lSy); CHKERRQ(ierr);
288 ierr = VecDestroy(&lSz); CHKERRQ(ierr);
289 ierr = VecDestroy(&lS_abs); CHKERRQ(ierr);
290 ierr = VecDestroy(&lLM); CHKERRQ(ierr);
291 ierr = VecDestroy(&lMM); CHKERRQ(ierr);
292
293
294 ierr = DMGlobalToLocalBegin(da, user->
CS, INSERT_VALUES, user->
lCs); CHKERRQ(ierr);
295 ierr = DMGlobalToLocalEnd(da, user->
CS, INSERT_VALUES, user->
lCs); CHKERRQ(ierr);
296
297 PetscReal max_norm;
298 ierr = VecMax(user->
CS, NULL, &max_norm); CHKERRQ(ierr);
300
302 PetscFunctionReturn(0);
303}
double ApplyLESTestFilter(const SimCtx *simCtx, double values[3][3][3], double weights[3][3][3])
Applies a numerical "test filter" to a 3x3x3 stencil of data points.
PetscErrorCode ComputeCellCharacteristicLengthScale(PetscReal ajc, Cmpnts csi, Cmpnts eta, Cmpnts zet, double *dx, double *dy, double *dz)
Computes characteristic length scales (dx, dy, dz) for a curvilinear cell.
#define GLOBAL
Scope for global logging across all processes.
#define LOG_ALLOW(scope, level, fmt,...)
Logging macro that checks both the log level and whether the calling function is in the allowed-funct...
#define PROFILE_FUNCTION_END
Marks the end of a profiled code block.
@ LOG_INFO
Informational messages about program execution.
@ LOG_DEBUG
Detailed debugging information.
#define PROFILE_FUNCTION_BEGIN
Marks the beginning of a profiled code block (typically a function).
PetscErrorCode ComputeVectorFieldDerivatives(UserCtx *user, PetscInt i, PetscInt j, PetscInt k, Cmpnts ***field_data, Cmpnts *dudx, Cmpnts *dvdx, Cmpnts *dwdx)
Computes the derivatives of a cell-centered vector field at a specific grid point.
SimCtx * simCtx
Back-pointer to the master simulation context.
A 3D point or vector with PetscScalar components.
The master context for the entire simulation.