35 use num_types,
only: rp, dp, sp
36 use case,
only: case_t
41 use scalar_ic,
only: set_scalar_ic
42 use checkpoint,
only: chkp_t
43 use chkp_output,
only: chkp_output_t
44 use flow_ic,
only: set_flow_ic
45 use output_controller,
only: output_controller_t
46 use file,
only: file_t
47 use json_module,
only: json_file
48 use json_utils,
only: json_get, json_get_or_default, json_extract_item
51 use logger,
only : neko_log
52 use time_state,
only : time_state_t
53 use utils,
only: neko_error
72 adjoint_convection_term
73 type(case_t),
pointer :: case
74 type(time_state_t) :: time
76 type(chkp_output_t) :: chkp_out
81 type(output_controller_t) :: output_controller
83 logical :: have_scalar = .false.
88 module procedure adjoint_init_from_json
94 subroutine adjoint_init_from_json(this, neko_case)
95 class(adjoint_case_t),
intent(inout) :: this
96 type(case_t),
target,
intent(inout) :: neko_case
98 this%case => neko_case
99 call adjoint_case_init_common(this, neko_case)
101 end subroutine adjoint_init_from_json
104 subroutine adjoint_case_init_common(this, neko_case)
105 class(adjoint_case_t),
target,
intent(inout) :: this
106 type(case_t),
intent(inout) :: neko_case
108 real(kind=rp) :: real_val = 0.0_rp
109 character(len=:),
allocatable :: string_val
111 integer :: n_scalars_primal, n_scalars_adjoint, i
112 logical :: scalar = .false.
113 logical :: temperature_found = .false.
116 type(json_file) :: ic_json, numerics_params
117 type(json_file) :: scalar_params_primal, scalar_params_adjoint, json_subdict
118 character(len=:),
allocatable :: json_key
119 logical :: dealias_adjoint_scalar_convection
124 call json_get(neko_case%params,
'case.fluid.scheme', string_val)
125 call adjoint_fluid_scheme_factory(this%fluid_adj, trim(string_val))
127 call json_get(neko_case%params,
'case.numerics.polynomial_order', lx)
130 this%chkp%tlag => this%time%tlag
131 this%chkp%dtlag => this%time%dtlag
133 select type (f => this%fluid_adj)
135 call f%init(neko_case%msh, lx, neko_case%params, &
136 neko_case%user, this%chkp)
145 n_scalars_adjoint = 0
146 if (neko_case%params%valid_path(
'case.adjoint_scalar'))
then
147 call json_get_or_default(neko_case%params, &
148 'case.adjoint_scalar.enabled', scalar, .true.)
149 n_scalars_adjoint = 1
151 else if (neko_case%params%valid_path(
'case.adjoint_scalars'))
then
152 call neko_case%params%info(
'case.adjoint_scalars', &
153 n_children = n_scalars_adjoint)
154 call neko_case%params%info(
'case.scalars', n_children = n_scalars_primal)
155 if (n_scalars_adjoint > 0)
then
160 this%have_scalar = scalar
167 if (this%have_scalar)
then
168 allocate(this%adjoint_scalars)
169 call json_get(neko_case%params,
'case.numerics', &
171 if (neko_case%params%valid_path(
'case.adjoint_scalar'))
then
173 call json_get(neko_case%params,
'case.adjoint_scalar', &
174 scalar_params_adjoint)
175 call json_get(neko_case%params,
'case.scalar', &
176 scalar_params_primal)
177 call this%adjoint_scalars%init(neko_case%msh, neko_case%fluid%c_Xh, &
178 neko_case%fluid%gs_Xh, scalar_params_adjoint, &
179 scalar_params_primal, numerics_params, neko_case%user, &
180 neko_case%chkp, neko_case%fluid%ulag, neko_case%fluid%vlag, &
181 neko_case%fluid%wlag, neko_case%fluid%ext_bdf, &
184 allocate(this%adjoint_convection_term)
186 call json_get_or_default(neko_case%params, &
187 'case.adjoint_scalar.dealias_coupling_term', &
188 dealias_adjoint_scalar_convection, .true.)
189 call this%adjoint_convection_term%init_from_components( &
190 this%fluid_adj%f_adj_x, this%fluid_adj%f_adj_y, &
191 this%fluid_adj%f_adj_z, this%case%scalars%scalar_fields(1)%s, &
192 this%adjoint_scalars%adjoint_scalar_fields(1)%s_adj, &
193 this%fluid_adj%c_Xh, this%fluid_adj%c_Xh_GL, &
194 this%fluid_adj%GLL_to_GL, &
195 dealias_adjoint_scalar_convection, this%fluid_adj%scratch_GL)
197 select type (f => this%fluid_adj)
200 call f%source_term%add(this%adjoint_convection_term)
205 call json_get(this%case%params, &
206 'case.adjoint_scalars', scalar_params_adjoint)
207 call json_get(this%case%params, &
208 'case.scalars', scalar_params_primal)
209 call this%adjoint_scalars%init(n_scalars_adjoint, n_scalars_primal, &
210 neko_case%msh, neko_case%fluid%c_Xh, neko_case%fluid%gs_Xh, &
211 scalar_params_adjoint, scalar_params_primal, numerics_params, &
212 neko_case%user, neko_case%chkp, neko_case%fluid%ulag, &
213 neko_case%fluid%vlag, neko_case%fluid%wlag, &
214 neko_case%fluid%ext_bdf, neko_case%fluid%rho)
215 call neko_error(
'The adjoint scaling coupling term have not yet' // &
216 'been implemented for multiple scalars')
223 call json_get(this%case%params,
'case.time', json_subdict)
224 call this%time%init(json_subdict)
247 call neko_log%section(
"Adjoint initial condition")
249 'case.adjoint_fluid.initial_condition',
'case.fluid.initial_condition')
251 call json_get(neko_case%params, json_key, ic_json)
252 call json_get(ic_json,
'type', string_val)
254 if (trim(string_val) .ne.
'user')
then
256 this%fluid_adj%u_adj, this%fluid_adj%v_adj, this%fluid_adj%w_adj, &
257 this%fluid_adj%p_adj, this%fluid_adj%c_Xh, this%fluid_adj%gs_Xh, &
261 this%fluid_adj%u_adj, this%fluid_adj%v_adj, this%fluid_adj%w_adj, &
262 this%fluid_adj%p_adj, this%fluid_adj%c_Xh, this%fluid_adj%gs_Xh, &
263 neko_case%user%initial_conditions, neko_case%fluid%name)
266 call neko_log%end_section()
268 if (this%have_scalar)
then
270 if (neko_case%params%valid_path(
'case.adjoint_scalar'))
then
272 call json_get(neko_case%params, &
273 'case.adjoint_scalar.initial_condition.type', string_val)
274 call json_get(neko_case%params, &
275 'case.adjoint_scalar.initial_condition', ic_json)
279 if (trim(string_val) .ne.
'user')
then
280 if (trim(neko_case%scalars%scalar_fields(1)%name) .eq. &
283 this%adjoint_scalars%adjoint_scalar_fields(1)%s_adj, &
284 this%adjoint_scalars%adjoint_scalar_fields(1)%c_Xh, &
285 this%adjoint_scalars%adjoint_scalar_fields(1)%gs_Xh, &
286 string_val, ic_json, 0)
289 this%adjoint_scalars%adjoint_scalar_fields(1)%s_adj, &
290 this%adjoint_scalars%adjoint_scalar_fields(1)%c_Xh, &
291 this%adjoint_scalars%adjoint_scalar_fields(1)%gs_Xh, &
292 string_val, ic_json, 1)
295 call neko_error(
"user ICs not implemented for adjoint scalar")
305 do i = 1, n_scalars_adjoint
306 call json_extract_item(neko_case%params,
'case.adjoint_scalars', &
307 i, scalar_params_adjoint)
308 call json_get(scalar_params_adjoint, &
309 'initial_condition.type', string_val)
310 call json_get(scalar_params_adjoint, &
311 'initial_condition', json_subdict)
313 if (trim(string_val) .ne.
'user')
then
314 if (trim(neko_case%scalars%scalar_fields(i)%name) .eq. &
317 this%adjoint_scalars%adjoint_scalar_fields(i)%s_adj, &
318 this%adjoint_scalars%adjoint_scalar_fields(i)%c_Xh, &
319 this%adjoint_scalars%adjoint_scalar_fields(i)%gs_Xh, &
320 string_val, json_subdict, 0)
321 temperature_found = .true.
323 if (temperature_found)
then
326 this%adjoint_scalars%adjoint_scalar_fields(i)%s_adj, &
327 this%adjoint_scalars%adjoint_scalar_fields(i)%c_Xh, &
328 this%adjoint_scalars%adjoint_scalar_fields(i)%gs_Xh, &
329 string_val, json_subdict, i - 1)
333 this%adjoint_scalars%adjoint_scalar_fields(i)%s_adj, &
334 this%adjoint_scalars%adjoint_scalar_fields(i)%c_Xh, &
335 this%adjoint_scalars%adjoint_scalar_fields(i)%gs_Xh, &
336 string_val, json_subdict, i)
340 call neko_error(
"user ICs not implemented for adjoint scalar")
347 select type (f => this%fluid_adj)
349 call f%ulag%set(f%u_adj)
350 call f%vlag%set(f%v_adj)
351 call f%wlag%set(f%w_adj)
357 call this%fluid_adj%validate
359 if (this%have_scalar)
then
360 call this%adjoint_scalars%validate()
366 call json_get_or_default(neko_case%params,
'case.output_precision', &
367 string_val,
'single')
369 if (trim(string_val) .eq.
'double')
then
378 call this%output_controller%init(this%time%end_time)
379 if (this%have_scalar)
then
381 this%adjoint_scalars, path = trim(neko_case%output_directory))
384 path = trim(neko_case%output_directory))
387 call json_get_or_default(neko_case%params,
'case.fluid.output_control',&
390 if (trim(string_val) .eq.
'org')
then
392 call json_get(neko_case%params,
'case.nsamples', real_val)
393 call this%output_controller%add(this%f_out, real_val,
'nsamples')
394 else if (trim(string_val) .eq.
'never')
then
396 call json_get_or_default(neko_case%params,
'case.fluid.output_value', &
398 call this%output_controller%add(this%f_out, 0.0_rp, string_val)
400 call json_get(neko_case%params,
'case.fluid.output_value', real_val)
401 call this%output_controller%add(this%f_out, real_val, string_val)
429 end subroutine adjoint_case_init_common
432 subroutine adjoint_free(this)
433 class(adjoint_case_t),
intent(inout) :: this
436 if (
allocated(this%adjoint_scalars))
then
437 call this%adjoint_scalars%free()
438 deallocate(this%adjoint_scalars)
441 if (
allocated(this%fluid_adj))
then
442 call this%fluid_adj%free()
443 deallocate(this%fluid_adj)
445 call this%output_controller%free()
447 end subroutine adjoint_free
449end module adjoint_case
Factory for all adjoint fluid schemes.
Adjoint Pn/Pn formulation.
Defines an output for a adjoint.
Implements the adjoint_scalar_convection_source_term type.
Contains the adjoint_scalar_pnpn_t type.
Contains the adjoint_scalar_scheme_t type.
Contains the adjoint_scalars_t type that manages multiple scalar fields.
Adjoint case type. Todo: This should Ideally be a subclass of case_t, however, that is not yet suppor...
Base type of all fluid formulations.
Base type for a scalar advection-diffusion solver.
Type to manage multiple adjoint scalar transport equations.