37 use gather_scatter,
only : gs_t, gs_op_add
38 use neko_config,
only : neko_bcknd_device
39 use num_types,
only : rp
40 use device_math,
only : device_col2
41 use device,
only : device_memcpy, host_to_device
42 use field,
only : field_t
43 use utils,
only : neko_error, filename_chsuffix, filename_suffix, &
44 neko_warning, neko_fname_len, extract_fld_file_index
45 use coefs,
only : coef_t
46 use math,
only : col2, cfill, cfill_mask
47 use json_module,
only : json_file
48 use json_utils,
only: json_get, json_get_or_default
49 use point_zone,
only: point_zone_t
50 use point_zone_registry,
only: neko_point_zone_registry
51 use registry,
only: neko_registry
52 use logger,
only: neko_log, log_size
53 use fld_file_data,
only: fld_file_data_t
54 use fld_file,
only: fld_file_t
55 use checkpoint,
only: chkp_t
56 use file,
only: file_t
57 use global_interpolation,
only: global_interpolation_t
58 use interpolation,
only: interpolator_t
59 use space,
only: space_t, gll
64 module procedure set_optimization_ic_int
85 subroutine set_optimization_ic_int(fld, coef, gs, params)
86 type(field_t),
intent(inout) :: fld
87 type(coef_t),
intent(in) :: coef
88 type(gs_t),
intent(inout) :: gs
89 type(json_file),
intent(inout) :: params
92 character(len=:),
allocatable :: type
93 real(kind=rp) :: ic_value
94 character(len=:),
allocatable :: read_str
95 character(len=:),
allocatable :: fname, mesh_fname
96 real(kind=rp) :: zone_value, tol
97 logical :: interpolate
99 call json_get(params,
"type", type)
101 select case (trim(type))
103 call json_get(params,
'value', ic_value)
104 call set_optimization_ic_uniform(fld, ic_value)
107 call json_get(params,
'base_value', ic_value)
108 call json_get(params,
'zone_name', read_str)
109 call json_get(params,
'zone_value', zone_value)
111 call set_optimization_ic_point_zone(fld, ic_value, read_str, zone_value)
114 call json_get(params,
'file_name', fname)
115 call json_get_or_default(params,
'interpolate', interpolate, .false.)
116 call json_get_or_default(params,
'tolerance', tol, 0.000001_rp)
117 call json_get_or_default(params,
'mesh_file_name', mesh_fname,
"none")
119 call set_optimization_ic_fld(fld, fname, interpolate, tol, mesh_fname)
122 call neko_error(
'Invalid initial condition')
126 call set_optimization_ic_common(fld, coef, gs)
128 end subroutine set_optimization_ic_int
136 subroutine set_optimization_ic_common(fld, coef, gs)
137 type(field_t),
intent(inout) :: fld
138 type(coef_t),
intent(in) :: coef
139 type(gs_t),
intent(inout) :: gs
143 if (neko_bcknd_device .eq. 1)
then
144 call device_memcpy(fld%x, fld%x_d, n, &
145 host_to_device, sync = .false.)
149 call gs%op(fld%x, n, gs_op_add)
151 if (neko_bcknd_device .eq. 1)
then
152 call device_col2(fld%x_d, coef%mult_d, n)
154 call col2(fld%x, coef%mult, n)
157 end subroutine set_optimization_ic_common
163 subroutine set_optimization_ic_uniform(fld, ic_value)
164 type(field_t),
intent(inout) :: fld
165 real(kind=rp),
intent(in) :: ic_value
167 character(len=LOG_SIZE) :: log_buf
169 call neko_log%message(
"Type : uniform")
170 write (log_buf,
'(A,ES12.6)')
"Value: ", ic_value
171 call neko_log%message(log_buf)
175 if (neko_bcknd_device .eq. 1)
then
176 call cfill(fld%x, ic_value, n)
179 end subroutine set_optimization_ic_uniform
188 subroutine set_optimization_ic_point_zone(fld, base_value, zone_name, &
190 type(field_t),
intent(inout) :: fld
191 real(kind=rp),
intent(in) :: base_value
192 character(len=*),
intent(in) :: zone_name
193 real(kind=rp),
intent(in) :: zone_value
196 character(len=LOG_SIZE) :: log_buf
197 class(point_zone_t),
pointer :: zone
200 call neko_log%message(
"Type : point_zone")
201 write (log_buf,
'(A,ES12.6)')
"Base value: ", base_value
202 call neko_log%message(log_buf)
203 call neko_log%message(
"Zone name : " // trim(zone_name))
204 write (log_buf,
'(A,ES12.6)')
"Zone value: ", zone_value
205 call neko_log%message(log_buf)
207 size = fld%dof%size()
208 zone => neko_point_zone_registry%get_point_zone(trim(zone_name))
210 call set_optimization_ic_uniform(fld, base_value)
211 call cfill_mask(fld%x, zone_value,
size, zone%mask%get(), zone%size)
213 end subroutine set_optimization_ic_point_zone
229 subroutine set_optimization_ic_fld(fld, file_name, &
230 interpolate, tolerance, mesh_file_name)
231 type(field_t),
intent(inout) :: fld
232 character(len=*),
intent(in) :: file_name
233 logical,
intent(in) :: interpolate
234 real(kind=rp),
intent(in) :: tolerance
235 character(len=*),
intent(inout) :: mesh_file_name
237 character(len=LOG_SIZE) :: log_buf
238 integer :: sample_idx, sample_mesh_idx
239 type(fld_file_data_t) :: fld_data
241 logical :: mesh_mismatch
244 type(global_interpolation_t) :: global_interp
248 type(space_t) :: prev_Xh
249 type(interpolator_t) :: space_interp
252 call neko_log%message(
"Type : field")
253 call neko_log%message(
"File name : " // trim(file_name))
254 write (log_buf,
'(A,L1)')
"Interpolation: ", interpolate
255 call neko_log%message(log_buf)
258 sample_idx = extract_fld_file_index(file_name, -1)
260 if (sample_idx .eq. -1)
then
261 call neko_error(
"Invalid file name for the initial condition. The " // &
262 "file format must be e.g. 'mean0.f00001'")
266 call filename_chsuffix(file_name, trim(file_name),
'fld')
269 call f%init(trim(file_name))
271 if (interpolate)
then
274 if (mesh_file_name .eq.
"none")
then
275 mesh_file_name = trim(file_name)
276 sample_mesh_idx = sample_idx
280 sample_mesh_idx = extract_fld_file_index(mesh_file_name, -1)
282 if (sample_mesh_idx .eq. -1)
then
283 call neko_error(
"Invalid file name for the initial condition." // &
284 " The file format must be e.g. 'mean0.f00001'")
287 write (log_buf,
'(A,ES12.6)')
"Tolerance : ", tolerance
288 call neko_log%message(log_buf)
289 write (log_buf,
'(A,A)')
"Mesh file : ", &
291 call neko_log%message(log_buf)
296 if (sample_mesh_idx .ne. sample_idx)
then
297 call f%set_counter(sample_mesh_idx)
298 call f%read(fld_data)
304 call f%set_counter(sample_idx)
305 call f%read(fld_data)
313 mesh_mismatch = (fld_data%glb_nelv .ne. fld%msh%glb_nelv .or. &
314 fld_data%gdim .ne. fld%msh%gdim)
316 if (mesh_mismatch .and. .not. interpolate)
then
317 call neko_error(
"The fld file must match the current mesh! " // &
318 "Use 'interpolate': 'true' to enable interpolation.")
319 else if (.not. mesh_mismatch .and. interpolate)
then
320 call neko_log%warning(
"You have activated interpolation but you " // &
321 "might still be using the same mesh.")
326 if (interpolate)
then
328 select type (ft => f%file_type)
330 if (.not. ft%dp_precision)
then
331 call neko_warning(
"The coordinates read from the field file " // &
332 "are in single precision.")
333 call neko_log%message(
"It is recommended to use a mesh in " // &
334 "double precision for better interpolation results.")
335 call neko_log%message(
"If the interpolation does not work, " // &
336 "you can try to increase the tolerance.")
342 call fld_data%generate_interpolator(global_interp, fld%dof, fld%msh, &
348 call global_interp%evaluate(fld%x, fld_data%u%x, on_host=.false.)
349 call global_interp%free()
354 call prev_xh%init(gll, fld_data%lx, fld_data%ly, fld_data%lz)
355 call space_interp%init(fld%Xh, prev_xh)
358 call space_interp%map_host(fld%x, fld_data%t%x, fld_data%nelv, fld%Xh)
360 call space_interp%free()
366 end subroutine set_optimization_ic_fld
Optimization initial condition.