Neko-TOP
A portable framework for high-order spectral element flow toplogy optimization.
Loading...
Searching...
No Matches
adjoint_curl_curl.f90
Go to the documentation of this file.
1
34!
84 use num_types, only: rp
85 use field, only: field_t
86 use coefs, only: coef_t
87 use gather_scatter, only: gs_t
88 use gs_ops, only: gs_op_add
89 use operators, only: opgrad, cdtp
90 use field_math, only: field_sub2, field_cmult
91 use neko_config, only: neko_bcknd_device
92 use math, only: col2
93 use device_math, only: device_col2
94 use facet_normal, only: facet_normal_t
95 use comm, only: neko_comm
96 use mpi_f08, only: mpi_allreduce, mpi_in_place, mpi_logical, mpi_lor
97 use utils, only: neko_error
98 implicit none
99 private
100
102
103contains
104
118 subroutine adjoint_curl_curl_check(prim_sym, adj_sym, cyclic)
119 type(facet_normal_t), intent(in) :: prim_sym, adj_sym
120 logical, intent(in) :: cyclic
121 logical :: has_sym
122
123 has_sym = prim_sym%marked_facet%size() .gt. 0 .or. &
124 adj_sym%marked_facet%size() .gt. 0
125 call mpi_allreduce(mpi_in_place, has_sym, 1, mpi_logical, mpi_lor, &
126 neko_comm)
127
128 if (has_sym) then
129 call neko_error("Symmetry boundaries " // &
130 "(case.fluid.boundary_conditions or " // &
131 "case.adjoint_fluid.boundary_conditions) are not supported " // &
132 "by the adjoint: the transpose of the curl-curl pressure " // &
133 "term on symmetry surfaces is not implemented.")
134 end if
135
136 if (cyclic) then
137 call neko_error("Cyclic boundaries (case.fluid.cyclic) are not " // &
138 "supported by the adjoint: the transpose of the cyclic " // &
139 "rotations in the curl-curl pressure term is not implemented.")
140 end if
141
142 end subroutine adjoint_curl_curl_check
143
170 subroutine adjoint_curl_curl_load(load_x, load_y, load_z, p_adj, coef, gs, &
171 mu, rho, work1, work2, work3, work4)
172 type(field_t), intent(inout) :: load_x, load_y, load_z
173 type(field_t), intent(in) :: p_adj
174 type(coef_t), intent(in) :: coef
175 type(gs_t), intent(inout) :: gs
176 real(kind=rp), intent(in) :: mu, rho
177 type(field_t), intent(inout) :: work1, work2, work3, work4
178
179 ! g = Binv gs(G p), so that B g = M^T G p; held in load
180 call opgrad(load_x%x, load_y%x, load_z%x, p_adj%x, coef)
181 call adjoint_curl_curl_gs_binv(load_x, load_y, load_z, coef, gs)
182
183 ! c = Binv gs(D_c^T B g), so that B c = M^T D_c^T M^T G p; held in
184 ! work1..3
185 call adjoint_curl_transpose(work1, work2, work3, load_x, load_y, load_z, &
186 work4, coef)
187 call adjoint_curl_curl_gs_binv(work1, work2, work3, coef, gs)
188
189 ! L = (mu / rho) D_c^T B c
190 call adjoint_curl_transpose(load_x, load_y, load_z, work1, work2, work3, &
191 work4, coef)
192 call field_cmult(load_x, mu / rho)
193 call field_cmult(load_y, mu / rho)
194 call field_cmult(load_z, mu / rho)
195
196 end subroutine adjoint_curl_curl_load
197
210 subroutine adjoint_curl_transpose(w1, w2, w3, y1, y2, y3, work, coef)
211 type(field_t), intent(inout) :: w1, w2, w3
212 type(field_t), intent(inout) :: y1, y2, y3
213 type(field_t), intent(inout) :: work
214 type(coef_t), intent(in) :: coef
215
216 call cdtp(w1%x, y2%x, coef%drdz, coef%dsdz, coef%dtdz, coef)
217 call cdtp(work%x, y3%x, coef%drdy, coef%dsdy, coef%dtdy, coef)
218 call field_sub2(w1, work)
219
220 call cdtp(w2%x, y3%x, coef%drdx, coef%dsdx, coef%dtdx, coef)
221 call cdtp(work%x, y1%x, coef%drdz, coef%dsdz, coef%dtdz, coef)
222 call field_sub2(w2, work)
223
224 call cdtp(w3%x, y1%x, coef%drdy, coef%dsdy, coef%dtdy, coef)
225 call cdtp(work%x, y2%x, coef%drdx, coef%dsdx, coef%dtdx, coef)
226 call field_sub2(w3, work)
227
228 end subroutine adjoint_curl_transpose
229
238 subroutine adjoint_curl_curl_gs_binv(y1, y2, y3, coef, gs)
239 type(field_t), intent(inout) :: y1, y2, y3
240 type(coef_t), intent(in) :: coef
241 type(gs_t), intent(inout) :: gs
242 integer :: n
243
244 n = y1%size()
245
246 call gs%op(y1, gs_op_add)
247 call gs%op(y2, gs_op_add)
248 call gs%op(y3, gs_op_add)
249
250 if (neko_bcknd_device .eq. 1) then
251 call device_col2(y1%x_d, coef%Binv_d, n)
252 call device_col2(y2%x_d, coef%Binv_d, n)
253 call device_col2(y3%x_d, coef%Binv_d, n)
254 else
255 call col2(y1%x, coef%Binv, n)
256 call col2(y2%x, coef%Binv, n)
257 call col2(y3%x, coef%Binv, n)
258 end if
259
260 end subroutine adjoint_curl_curl_gs_binv
261
262end module adjoint_curl_curl
Adjoint of the curl-curl term in the Pn/Pn pressure residual.
subroutine, public adjoint_curl_curl_check(prim_sym, adj_sym, cyclic)
Stop with an error if the boundary conditions make the adjoint curl-curl load differ from the transpo...
subroutine, public adjoint_curl_curl_load(load_x, load_y, load_z, p_adj, coef, gs, mu, rho, work1, work2, work3, work4)
Compute the adjoint curl-curl load .