Neko 1.99.2
A portable framework for high-order spectral element flow simulations
Loading...
Searching...
No Matches
pnpn_res_stress_cpu.f90
Go to the documentation of this file.
1
3 use gather_scatter, only : gs_t, gs_op_add
5 use field, only : field_t
6 use ax_product, only : ax_t
7 use coefs, only : coef_t
11 use mesh, only : mesh_t
12 use num_types, only : rp
13 use space, only : space_t
14 use math, only : rzero, vdot3, cmult, sub2, col2, copy, invers2, cmult2
15 use, intrinsic :: iso_c_binding, only : c_ptr
16 implicit none
17 private
18
21 type, public, extends(pnpn_prs_res_t) :: pnpn_prs_res_stress_cpu_t
22 contains
23 procedure, nopass :: compute => pnpn_prs_res_stress_cpu_compute
25
28 type, public, extends(pnpn_vel_res_t) :: pnpn_vel_res_stress_cpu_t
29 contains
30 procedure, nopass :: compute => pnpn_vel_res_stress_cpu_compute
32
33contains
34
35 subroutine pnpn_prs_res_stress_cpu_compute(p, p_res, u, v, w, u_e, v_e, w_e,&
36 f_x, f_y, f_z, c_Xh, gs_Xh, bc_prs_surface, bc_sym_surface, Ax, bd, dt,&
37 mu, rho, event)
38 type(field_t), intent(inout) :: p, u, v, w
39 type(field_t), intent(in) :: u_e, v_e, w_e
40 type(field_t), intent(inout) :: p_res
41 type(field_t), intent(in) :: f_x, f_y, f_z
42 type(coef_t), intent(inout) :: c_Xh
43 type(gs_t), intent(inout) :: gs_Xh
44 type(facet_normal_t), intent(in) :: bc_prs_surface
45 type(facet_normal_t), intent(in) :: bc_sym_surface
46 class(ax_t), intent(inout) :: Ax
47 real(kind=rp), intent(in) :: bd
48 real(kind=rp), intent(in) :: dt
49 type(field_t), intent(in) :: mu
50 type(field_t), intent(in) :: rho
51 type(c_ptr), intent(inout) :: event
52 real(kind=rp) :: dtbd
53 integer :: n, nelv, lxyz
54 integer :: i, e
55 ! Work arrays
56 type(field_t), pointer :: ta1, ta2, ta3, wa1, wa2, wa3, work1, work2, work3
57 type(field_t), pointer :: s11, s22, s33, s12, s13, s23
58 integer :: temp_indices(15)
59
60 ! Work arrays
61 call neko_scratch_registry%request_field(ta1, temp_indices(1), .false.)
62 call neko_scratch_registry%request_field(ta2, temp_indices(2), .false.)
63 call neko_scratch_registry%request_field(ta3, temp_indices(3), .false.)
64 call neko_scratch_registry%request_field(wa1, temp_indices(4), .false.)
65 call neko_scratch_registry%request_field(wa2, temp_indices(5), .false.)
66 call neko_scratch_registry%request_field(wa3, temp_indices(6), .false.)
67 call neko_scratch_registry%request_field(work1, temp_indices(7), .false.)
68 call neko_scratch_registry%request_field(work2, temp_indices(8), .false.)
69 call neko_scratch_registry%request_field(work3, temp_indices(9), .false.)
70
71 ! Stress tensor
72 call neko_scratch_registry%request_field(s11, temp_indices(10), .false.)
73 call neko_scratch_registry%request_field(s22, temp_indices(11), .false.)
74 call neko_scratch_registry%request_field(s33, temp_indices(12), .false.)
75 call neko_scratch_registry%request_field(s12, temp_indices(13), .false.)
76 call neko_scratch_registry%request_field(s13, temp_indices(14), .false.)
77 call neko_scratch_registry%request_field(s23, temp_indices(15), .false.)
78
79 n = c_xh%dof%size()
80 lxyz = c_xh%Xh%lxyz
81 nelv = c_xh%msh%nelv
82
83 call invers2(c_xh%h1, rho%x, n)
84 call rzero(c_xh%h2, n)
85 c_xh%ifh2 = .false.
86
87 ! mu times the double curl of the velocity
88 call curl(ta1, ta2, ta3, u_e, v_e, w_e, work1, work2, c_xh)
89 call curl(wa1, wa2, wa3, ta1, ta2, ta3, work1, work2, c_xh)
90
91 call col2(wa1%x, mu%x, n)
92 call col2(wa2%x, mu%x, n)
93 call col2(wa3%x, mu%x, n)
94
95
96 ! The strain rate tensor
97 call strain_rate(s11%x, s22%x, s33%x, s12%x, s13%x, s23%x, &
98 u_e, v_e, w_e, c_xh)
99
100
101 ! Gradient of viscosity * 2
102 call dudxyz(ta1%x, mu%x, c_xh%drdx, c_xh%dsdx, c_xh%dtdx, c_xh)
103 call dudxyz(ta2%x, mu%x, c_xh%drdy, c_xh%dsdy, c_xh%dtdy, c_xh)
104 call dudxyz(ta3%x, mu%x, c_xh%drdz, c_xh%dsdz, c_xh%dtdz, c_xh)
105
106 call cmult(ta1%x, 2.0_rp, n)
107 call cmult(ta2%x, 2.0_rp, n)
108 call cmult(ta3%x, 2.0_rp, n)
109
110 ! S^T grad \mu
111 do e = 1, nelv
112 call vdot3(work1%x(:, :, :, e), &
113 ta1%x(:, :, :, e), ta2%x(:, :, :, e), ta3%x(:, :, :, e), &
114 s11%x(:, :, :, e), s12%x(:, :, :, e), s13%x(:, :, :, e), &
115 lxyz)
116
117 call vdot3 (work2%x(:, :, :, e), &
118 ta1%x(:, :, :, e), ta2%x(:, :, :, e), ta3%x(:, :, :, e), &
119 s12%x(:, :, :, e), s22%x(:, :, :, e), s23%x(:, :, :, e), &
120 lxyz)
121
122 call vdot3 (work3%x(:, :, :, e), &
123 ta1%x(:, :, :, e), ta2%x(:, :, :, e), ta3%x(:, :, :, e), &
124 s13%x(:, :, :, e), s23%x(:, :, :, e), s33%x(:, :, :, e), &
125 lxyz)
126 end do
127
128 ! Subtract the two terms of the viscous stress to get
129 ! \nabla x \nabla u - S^T \nabla \mu
130 ! The sign is consitent with the fact that we subtract the term
131 ! below.
132 call sub2(wa1%x, work1%x, n)
133 call sub2(wa2%x, work2%x, n)
134 call sub2(wa3%x, work3%x, n)
135
136 do concurrent(i = 1:n)
137 ta1%x(i,1,1,1) = f_x%x(i,1,1,1) / rho%x(i,1,1,1) &
138 - ((wa1%x(i,1,1,1) / rho%x(i,1,1,1)) * c_xh%B(i,1,1,1))
139 ta2%x(i,1,1,1) = f_y%x(i,1,1,1) / rho%x(i,1,1,1) &
140 - ((wa2%x(i,1,1,1) / rho%x(i,1,1,1)) * c_xh%B(i,1,1,1))
141 ta3%x(i,1,1,1) = f_z%x(i,1,1,1) / rho%x(i,1,1,1) &
142 - ((wa3%x(i,1,1,1) / rho%x(i,1,1,1)) * c_xh%B(i,1,1,1))
143 end do
144
145 call rotate_cyc(ta1%x, ta2%x, ta3%x, 1, c_xh)
146 call gs_xh%op(ta1, gs_op_add)
147 call gs_xh%op(ta2, gs_op_add)
148 call gs_xh%op(ta3, gs_op_add)
149 call rotate_cyc(ta1%x, ta2%x, ta3%x, 0, c_xh)
150
151 do i = 1, n
152 ta1%x(i,1,1,1) = ta1%x(i,1,1,1) * c_xh%Binv(i,1,1,1)
153 ta2%x(i,1,1,1) = ta2%x(i,1,1,1) * c_xh%Binv(i,1,1,1)
154 ta3%x(i,1,1,1) = ta3%x(i,1,1,1) * c_xh%Binv(i,1,1,1)
155 end do
156
157 ! Compute the components of the divergence of the rhs
158 call cdtp(wa1%x, ta1%x, c_xh%drdx, c_xh%dsdx, c_xh%dtdx, c_xh)
159 call cdtp(wa2%x, ta2%x, c_xh%drdy, c_xh%dsdy, c_xh%dtdy, c_xh)
160 call cdtp(wa3%x, ta3%x, c_xh%drdz, c_xh%dsdz, c_xh%dtdz, c_xh)
161
162 ! The laplacian of the pressure
163 call ax%compute(p_res%x, p%x, c_xh, p%msh, p%Xh)
164
165 do i = 1, n
166 p_res%x(i,1,1,1) = (-p_res%x(i,1,1,1)) &
167 + wa1%x(i,1,1,1) + wa2%x(i,1,1,1) + wa3%x(i,1,1,1)
168 end do
169
170 !
171 ! Surface velocity terms
172 !
173 do i = 1, n
174 wa1%x(i,1,1,1) = 0.0_rp
175 wa2%x(i,1,1,1) = 0.0_rp
176 wa3%x(i,1,1,1) = 0.0_rp
177 end do
178
179 call bc_sym_surface%apply_surfvec(wa1%x, wa2%x, wa3%x, ta1%x, ta2%x, ta3%x,&
180 n)
181
182 dtbd = bd / dt
183 do i = 1, n
184 ta1%x(i,1,1,1) = 0.0_rp
185 ta2%x(i,1,1,1) = 0.0_rp
186 ta3%x(i,1,1,1) = 0.0_rp
187 end do
188
189 call bc_prs_surface%apply_surfvec(ta1%x, ta2%x, ta3%x, u%x, v%x, w%x, n)
190
191 do i = 1, n
192 p_res%x(i,1,1,1) = p_res%x(i,1,1,1) &
193 - (dtbd * (ta1%x(i,1,1,1) + ta2%x(i,1,1,1) + ta3%x(i,1,1,1)))&
194 - (wa1%x(i,1,1,1) + wa2%x(i,1,1,1) + wa3%x(i,1,1,1))
195 end do
196
197 call neko_scratch_registry%relinquish_field(temp_indices)
198
200
201 subroutine pnpn_vel_res_stress_cpu_compute(Ax, u, v, w, u_res, v_res, w_res, &
202 p, f_x, f_y, f_z, c_Xh, msh, Xh, mu, rho, bd, dt, n)
203 class(ax_t), intent(in) :: Ax
204 type(mesh_t), intent(inout) :: msh
205 type(space_t), intent(inout) :: Xh
206 type(field_t), intent(inout) :: p, u, v, w
207 type(field_t), intent(inout) :: u_res, v_res, w_res
208 type(field_t), intent(in) :: f_x, f_y, f_z
209 type(coef_t), intent(inout) :: c_Xh
210 type(field_t), intent(in) :: mu
211 type(field_t), intent(in) :: rho
212 real(kind=rp), intent(in) :: bd
213 real(kind=rp), intent(in) :: dt
214 integer :: temp_indices(3)
215 type(field_t), pointer :: ta1, ta2, ta3
216 integer, intent(in) :: n
217 integer :: i
218
219 call copy(c_xh%h1, mu%x, n)
220 call cmult2(c_xh%h2, rho%x, bd / dt, n)
221 c_xh%ifh2 = .true.
222
223 ! Viscous stresses
224 call ax%compute_vector(u_res%x, v_res%x, w_res%x, u%x, v%x, w%x, c_xh,&
225 msh, xh)
226
227 call neko_scratch_registry%request_field(ta1, temp_indices(1), .false.)
228 call neko_scratch_registry%request_field(ta2, temp_indices(2), .false.)
229 call neko_scratch_registry%request_field(ta3, temp_indices(3), .false.)
230
231 ! Pressure gradient
232 call opgrad(ta1%x, ta2%x, ta3%x, p%x, c_xh)
233
234 ! Sum all the terms
235 do i = 1, n
236 u_res%x(i,1,1,1) = (-u_res%x(i,1,1,1)) - ta1%x(i,1,1,1) + f_x%x(i,1,1,1)
237 v_res%x(i,1,1,1) = (-v_res%x(i,1,1,1)) - ta2%x(i,1,1,1) + f_y%x(i,1,1,1)
238 w_res%x(i,1,1,1) = (-w_res%x(i,1,1,1)) - ta3%x(i,1,1,1) + f_z%x(i,1,1,1)
239 end do
240
241 call neko_scratch_registry%relinquish_field(temp_indices)
242
244
245end module pnpn_res_stress_cpu
Defines a Matrix-vector product.
Definition ax.f90:34
Coefficients.
Definition coef.f90:34
Dirichlet condition applied in the facet normal direction.
Defines a field.
Definition field.f90:34
Gather-scatter.
Definition math.f90:60
subroutine, public cmult(a, c, n)
Multiplication by constant c .
Definition math.f90:411
subroutine, public cmult2(a, b, c, n)
Multiplication by constant c .
Definition math.f90:423
subroutine, public invers2(a, b, n)
Compute inverted vector .
Definition math.f90:639
subroutine, public col2(a, b, n)
Vector multiplication .
Definition math.f90:854
subroutine, public copy(a, b, n)
Copy a vector .
Definition math.f90:249
subroutine, public vdot3(dot, u1, u2, u3, v1, v2, v3, n)
Compute a dot product (3-d version) assuming vector components etc.
Definition math.f90:684
subroutine, public rzero(a, n)
Zero a real vector.
Definition math.f90:205
subroutine, public sub2(a, b, n)
Vector substraction .
Definition math.f90:768
Defines a mesh.
Definition mesh.f90:34
integer, parameter, public rp
Global precision used in computations.
Definition num_types.f90:12
Operators.
Definition operators.f90:34
subroutine, public opgrad(ux, uy, uz, u, coef, es, ee)
Compute the weak gradient of a scalar field, i.e. the gradient multiplied by the mass matrix.
subroutine, public curl(w1, w2, w3, u1, u2, u3, work1, work2, coef, event)
subroutine, public strain_rate(s11, s22, s33, s12, s13, s23, u, v, w, coef)
Compute the strain rate tensor, i.e 0.5 * du_i/dx_j + du_j/dx_i.
subroutine, public cdtp(dtx, x, dr, ds, dt, coef, es, ee)
Apply D^T to a scalar field, where D is the derivative matrix.
subroutine, public dudxyz(du, u, dr, ds, dt, coef)
Compute derivative of a scalar field along a single direction.
Definition operators.f90:90
Residuals in the Pn-Pn formulation (CPU version)
subroutine pnpn_prs_res_stress_cpu_compute(p, p_res, u, v, w, u_e, v_e, w_e, f_x, f_y, f_z, c_xh, gs_xh, bc_prs_surface, bc_sym_surface, ax, bd, dt, mu, rho, event)
subroutine pnpn_vel_res_stress_cpu_compute(ax, u, v, w, u_res, v_res, w_res, p, f_x, f_y, f_z, c_xh, msh, xh, mu, rho, bd, dt, n)
Defines Pressure and velocity residuals in the Pn-Pn formulation.
Definition pnpn_res.f90:34
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.
Defines a function space.
Definition space.f90:34
Base type for a matrix-vector product providing .
Definition ax.f90:43
Coefficients defined on a given (mesh, ) tuple. Arrays use indices (i,j,k,e): element e,...
Definition coef.f90:56
Dirichlet condition in facet normal direction.
CPU implementation of the pressure residual for the PnPn fluid with full viscous stress formulation.
CPU implementation of the velocity residual for the PnPn fluid with full viscous stress formulation.
Abstract type to compute pressure residual.
Definition pnpn_res.f90:48
Abstract type to compute velocity residual.
Definition pnpn_res.f90:54
The function space for the SEM solution fields.
Definition space.f90:63