38 use json_module,
only : json_file
66 real(kind=
rp) :: kappa
72 real(kind=
rp) :: z0h_in
80 character(len=:),
allocatable :: bc_type
82 real(kind=
rp) :: bc_value
84 character(len=:),
allocatable :: scalar_name
86 type(
vector_t) :: ri_b, l_ob, utau, magu, ti, ts, q
88 type(
vector_t) :: u_s, v_s, w_s, temp_s, temp_w
98 procedure, pass(this) :: init_from_components => &
115 subroutine most_init(this, scheme_name, coef, msk, facet, &
117 class(
most_t),
intent(inout) :: this
118 character(len=*),
intent(in) :: scheme_name
119 type(
coef_t),
intent(in) :: coef
120 integer,
intent(in) :: msk(:)
121 integer,
intent(in) :: facet(:)
122 type(json_file),
intent(inout) :: json
123 real(kind=
rp) :: kappa, z0, z0h_in, pr
124 character(len=:),
allocatable :: bc_type
125 character(len=:),
allocatable :: scalar_name
126 real(kind=
rp) :: bc_value
127 real(kind=
rp),
allocatable :: g_tmp(:)
128 real(kind=
rp) :: g(3)
129 logical :: if_time_dependent
141 call json_get(json,
"type_of_temp_bc", bc_type)
142 call json_get(json,
"scalar_field", scalar_name)
145 if_time_dependent, .false.)
147 if (if_time_dependent)
then
152 if (
size(g_tmp) == 3)
then
155 call neko_error(
"MOST WM: The gravity vector should have " // &
156 "exactly 3 components")
161 call this%init_from_components(scheme_name, scalar_name, coef, msk, &
163 kappa, g, pr, z0, z0h_in, bc_type, bc_value)
165 deallocate(scalar_name)
172 class(
most_t),
intent(inout) :: this
173 type(
coef_t),
intent(in) :: coef
174 character(len=*),
intent(in) :: scheme_name
175 type(json_file),
intent(inout) :: json
176 real(kind=
rp),
allocatable :: g_tmp(:)
177 character(len=LOG_SIZE) :: log_buf
178 logical :: if_time_dependent
180 call this%partial_init_base(coef, scheme_name, json)
185 call json_get(json,
"type_of_temp_bc", this%bc_type)
186 call json_get(json,
"scalar_field", this%scalar_name)
189 if_time_dependent, .false.)
191 if (if_time_dependent)
then
197 if (
size(g_tmp) == 3)
then
200 call neko_error(
"MOST WM: The gravity vector should have " // &
201 "exactly 3 components")
206 write(log_buf,
'(A, A)')
'Model : MOST'
208 write(log_buf,
'(A, A)')
'scalar_name : ', trim(this%scalar_name)
210 write(log_buf,
'(A, A)')
'bc_type : ', trim(this%bc_type)
212 write(log_buf,
'(A, E15.7)')
'bc_value : ', this%bc_value
214 write(log_buf,
'(A, E15.7)')
'kappa : ', this%kappa
216 write(log_buf,
'(A, E15.7)')
'z0 : ', this%z0
218 write(log_buf,
'(A, E15.7)')
'z0h : ', this%z0h_in
220 write(log_buf,
'(A, E15.7)')
'Pr : ', this%Pr
222 write(log_buf,
'(A, 3(E15.7,1X))')
'g : ', this%g
232 class(
most_t),
intent(inout) :: this
233 integer,
intent(in) :: msk(:)
234 integer,
intent(in) :: facet(:)
235 character(len=*),
optional,
intent(in) :: bc_name
236 type(
user_t),
target,
optional,
intent(in) :: user
237 call this%finalize_base(msk, facet, bc_name,
user)
238 call this%validate_single_sample()
240 call this%Ri_b%init(this%n_nodes)
241 call this%L_ob%init(this%n_nodes)
242 call this%utau%init(this%n_nodes)
243 call this%magu%init(this%n_nodes)
244 call this%ti%init(this%n_nodes)
245 call this%ts%init(this%n_nodes)
246 call this%q%init(this%n_nodes)
248 call this%mu_w%init(this%n_nodes)
249 call this%rho_w%init(this%n_nodes)
250 call this%u_s%init(this%n_nodes)
251 call this%v_s%init(this%n_nodes)
252 call this%w_s%init(this%n_nodes)
253 call this%temp_s%init(this%n_nodes)
254 call this%temp_w%init(this%n_nodes)
260 class(
most_t),
intent(inout) :: this
265 this%mu%size(), this%mu_w%size())
268 this%rho%size(), this%rho_w%size())
271 this%mu%size(), this%mu_w%size())
273 this%rho%size(), this%rho_w%size())
292 coef, msk, facet, sampler, kappa, g, Pr, z0, &
293 z0h_in, bc_type, bc_value)
294 class(
most_t),
intent(inout) :: this
295 character(len=*),
intent(in) :: scheme_name
296 character(len=*),
intent(in) :: bc_type
297 character(len=*),
intent(in) :: scalar_name
298 type(
coef_t),
intent(in) :: coef
299 integer,
intent(in) :: msk(:)
300 integer,
intent(in) :: facet(:)
302 real(kind=
rp),
intent(in) :: g(3)
303 real(kind=
rp) :: g_mag, g_dot_n, cos_alpha, max_ang
305 real(kind=
rp),
intent(in) :: kappa
306 real(kind=
rp),
intent(in) :: z0, z0h_in, bc_value, pr
307 character(len=LOG_SIZE) :: log_buf
310 call this%init_base(scheme_name, coef, msk, facet, sampler)
317 this%bc_type = bc_type
318 this%bc_value = bc_value
319 this%scalar_name = scalar_name
321 call this%mu_w%init(this%n_nodes)
322 call this%rho_w%init(this%n_nodes)
323 call this%validate_single_sample()
324 call this%u_s%init(this%n_nodes)
325 call this%v_s%init(this%n_nodes)
326 call this%w_s%init(this%n_nodes)
327 call this%temp_s%init(this%n_nodes)
328 call this%temp_w%init(this%n_nodes)
331 g_mag = sqrt(sum(g**2))
332 if (g_mag < 1.0e-6_rp)
then
333 call neko_error(
"MOST WM: Gravity magnitude is zero. Check " // &
334 "your input configuration.")
339 do i = 1, this%n_nodes
340 g_dot_n = abs(g(1) * this%n_x%x(i) + g(2) * this%n_y%x(i) + &
341 g(3) * this%n_z%x(i))
342 cos_alpha = g_dot_n / g_mag
343 max_ang =
max(max_ang, acos(min(1.0_rp, cos_alpha)))
345 max_ang = max_ang * 180.0_rp / (4.0_rp * atan(1.0_rp))
346 if (max_ang > 8.0_rp)
then
347 write(log_buf,
'(A, F6.2, A)') &
348 "MOST WM: Significant gravity-normal misalignment (max ", &
349 max_ang,
" deg). Stability corrections will use projected gravity."
358 class(
most_t),
intent(in) :: this
360 if (any(this%sampler%h%x(1:this%n_nodes) .le. this%z0))
then
361 call neko_error(
"MOST WM: Sampling height h must be greater " // &
362 "than roughness z0.")
363 else if ((this%z0h_in .gt. 0.0_rp) .and. &
364 any(this%sampler%h%x(1:this%n_nodes) .le. this%z0h_in))
then
365 call neko_error(
"MOST WM: Sampling height h must be greater " // &
366 "than thermal roughness z0h.")
367 else if (this%z0 .eq. 0.0_rp)
then
368 call neko_error(
"MOST WM: Roughness z0 must be greater than 0.")
369 else if (this%z0h_in .eq. 0.0_rp)
then
370 call neko_error(
"MOST WM: Thermal roughness z0h must be greater than 0.")
376 class(
most_t),
intent(inout) :: this
378 if (
allocated(this%bc_type))
then
379 deallocate(this%bc_type)
382 if (
allocated(this%scalar_name))
then
383 deallocate(this%scalar_name)
386 call this%mu_w%free()
387 call this%rho_w%free()
391 call this%temp_s%free()
392 call this%temp_w%free()
393 call this%free_base()
395 call this%Ri_b%free()
396 call this%L_ob%free()
397 call this%utau%free()
398 call this%magu%free()
409 class(
most_t),
intent(inout) :: this
410 real(kind=
rp),
intent(in) :: t
411 integer,
intent(in) :: tstep
416 real(kind=
rp),
pointer :: updated_bc_value
419 call this%extract_properties()
426 call this%sampler%sample(u, this%u_s)
427 call this%sampler%sample(v, this%v_s)
428 call this%sampler%sample(w, this%w_s)
429 call this%sampler%sample(temp, this%temp_s)
432 this%msk_d, temp%size(), this%n_nodes)
435 temp%size(), this%n_nodes)
440 this%bc_value = updated_bc_value
445 this%temp_s%x_d, this%temp_w%x_d, this%n_x%x_d, &
446 this%n_y%x_d, this%n_z%x_d, this%sampler%h%x_d, &
447 this%tau_x%x_d, this%tau_y%x_d, &
448 this%tau_z%x_d, this%n_nodes, this%kappa, &
449 this%mu_w%x_d, this%rho_w%x_d, this%g, this%Pr, this%z0, &
451 this%bc_type, this%bc_value, tstep, this%Ri_b%x_d, &
452 this%L_ob%x_d, this%utau%x_d, this%magu%x_d, this%ti%x_d, &
453 this%ts%x_d, this%q%x_d)
456 this%temp_s%x, this%temp_w%x, this%n_x%x, &
457 this%n_y%x, this%n_z%x, this%sampler%h%x, this%tau_x%x, &
458 this%tau_y%x, this%tau_z%x, this%n_nodes, &
459 this%kappa, this%mu_w%x, this%rho_w%x, &
460 this%g, this%Pr, this%z0, this%z0h_in, this%bc_type, &
461 this%bc_value, tstep, this%Ri_b%x, this%L_ob%x, &
462 this%utau%x, this%magu%x, this%ti%x, this%ts%x, &
467 this%utau, this%magu, this%ti, this%ts, this%q, &
468 this%n_nodes, this%bc_value)
470 nullify(u, v, w, temp, updated_bc_value)
476 character(len=LOG_SIZE) :: log_buf
477 integer,
intent(in) :: n_nodes
478 real(kind=
rp),
intent(in) :: bc_value
479 type(
vector_t),
intent(in) :: ri_b, l_ob, utau
480 type(
vector_t),
intent(in) :: magu, ti, ts, q
482 call neko_log%section(
"Wall model diagnostics")
483 write(log_buf,
'(A)')
'--- sum --- '
484 call neko_log%message(trim(log_buf))
485 write(log_buf,
'(A,3E15.7)')
"Ri_b: ",&
488 call neko_log%message(trim(log_buf))
490 write(log_buf,
'(A,3E15.7)')
"L_ob: ", &
493 call neko_log%message(trim(log_buf))
495 write(log_buf,
'(A,3E15.7)')
"utau: ", &
498 call neko_log%message(trim(log_buf))
500 write(log_buf,
'(A,3E15.7)')
"magu: ", &
503 call neko_log%message(trim(log_buf))
505 write(log_buf,
'(A,3E15.7)')
"ti: ", &
508 call neko_log%message(trim(log_buf))
510 write(log_buf,
'(A,3E15.7)')
"ts: ", &
513 call neko_log%message(trim(log_buf))
515 write(log_buf,
'(A,3E15.7)')
"q: ", &
518 call neko_log%message(trim(log_buf))
520 write(log_buf,
'(A,E15.7)')
"bc_value: ", bc_value
521 call neko_log%message(trim(log_buf))
__inline__ __device__ void nonlinear_index(const int idx, const int lx, int *index)
__global__ void most_compute(const T *__restrict__ u_d, const T *__restrict__ v_d, const T *__restrict__ w_d, const T *__restrict__ temp_d, const T *__restrict__ temp_w_d, const T *__restrict__ h_d, const T *__restrict__ n_x_d, const T *__restrict__ n_y_d, const T *__restrict__ n_z_d, T *__restrict__ tau_x_d, T *__restrict__ tau_y_d, T *__restrict__ tau_z_d, int n_nodes, T kappa, const T *__restrict__ mu_w_d, const T *__restrict__ rho_w_d, T g1, T g2, T g3, T Pr, T z0, T z0h_in, T bc_value, T *__restrict__ Ri_b_diagn, T *__restrict__ L_ob_diagn, T *__restrict__ utau_diagn, T *__restrict__ magu_diagn, T *__restrict__ ti_diagn, T *__restrict__ ts_diagn, T *__restrict__ q_diagn)
Retrieves a parameter by name or assigns a provided default value. In the latter case also adds the m...
Retrieves a parameter by name or throws an error.
subroutine, public device_masked_gather_copy_0(a_d, b_d, mask_d, n, n_mask, strm)
Gather a masked vector .
Utilities for retrieving parameters from the case files.
type(log_t), public neko_log
Global log stream.
integer, parameter, public log_size
subroutine, public masked_gather_copy_0(a, b, mask, n, n_mask)
Gather a masked vector to reduced contigous vector .
Implements the CPU kernel for the most_t type.
subroutine, public most_compute_cpu(u, v, w, temp, temp_w, n_x, n_y, n_z, h, tau_x, tau_y, tau_z, n_nodes, kappa, mu_w, rho_w, g_vec, pr, z0, z0h_in, bc_type, bc_value, tstep, ri_b_diagn, l_ob_diagn, utau_diagn, magu_diagn, ti_diagn, ts_diagn, q_diagn)
Main routine to compute the surface stresses based on MOST.
Implements the device kernel for the most_t type.
subroutine, public most_compute_device(u_d, v_d, w_d, temp_d, temp_w_d, n_x_d, n_y_d, n_z_d, h_d, tau_x_d, tau_y_d, tau_z_d, n_nodes, kappa, mu_w_d, rho_w_d, g, pr, z0, z0h_in, bc_type, bc_value, tstep, ri_b_diagn, l_ob_diagn, utau_diagn, magu_diagn, ti_diagn, ts_diagn, q_diagn)
Compute the wall shear stress on device using the rough log-law model.
subroutine most_validate_sampling_height(this)
subroutine most_init_from_components(this, scheme_name, scalar_name, coef, msk, facet, sampler, kappa, g, pr, z0, z0h_in, bc_type, bc_value)
Constructor from components.
subroutine most_free(this)
Destructor for the most_t (base) class.
subroutine most_log_diagnostics(ri_b, l_ob, utau, magu, ti, ts, q, n_nodes, bc_value)
subroutine most_partial_init(this, coef, scheme_name, json)
Constructor from JSON.
subroutine most_init(this, scheme_name, coef, msk, facet, json)
Constructor from JSON.
subroutine most_extract_properties(this)
Extract the values of rho and mu at the boundary.
subroutine most_finalize(this, msk, facet, bc_name, user)
Finalize the construction using the mask and facet arrays of the bc.
integer, parameter neko_bcknd_device
integer, parameter, public rp
Global precision used in computations.
Defines a registry for storing solution fields.
type(registry_t), target, public neko_registry
Global field registry.
type(registry_t), target, public neko_const_registry
This registry is used to store user-defined scalars and vectors, provided under the constants section...
Defines a registry for storing and requesting temporary objects This can be used when you have a func...
type(scratch_registry_t), target, public neko_scratch_registry
Global scratch registry.
Interfaces for user interaction with NEKO.
subroutine, public neko_warning(warning_msg)
Reports a warning to standard output.
real(kind=rp) function, public vector_glmin(a, n)
Global minimum of all elements in a vector .
real(kind=rp) function, public vector_glsum(a, n)
real(kind=rp) function, public vector_glmax(a, n)
Global maximum of all elements in a vector .
Factory for wall-model samplers.
subroutine, public wall_sampler_factory(object, json)
Wall sampler factory.
Defines the abstract interface for wall-model field samplers.
Coefficients defined on a given (mesh, ) tuple. Arrays use indices (i,j,k,e): element e,...
Wall model based on the Monin-Obukhov Similarity Theory for atmospheric boundary layer flows....
A type collecting all the overridable user routines and flag to suppress type injection from custom m...
Base abstract type for wall-stress models for wall-modelled LES.
Base type for sampling solution fields at points associated with wall nodes. Samples belonging to one...