FE-Project
Loading...
Searching...
No Matches
scale_mesh_cubedspheredom3d.F90
Go to the documentation of this file.
1!-------------------------------------------------------------------------------
9#include "scaleFElib.h"
11
12 !-----------------------------------------------------------------------------
13 !
14 !++ used modules
15 !
16 use scale_io
17 use scale_precision
18
19 use scale_mesh_base3d, only: &
27
28 use scale_mesh_base2d, only: &
35
37
38 !-----------------------------------------------------------------------------
39 implicit none
40 private
41
42 !-----------------------------------------------------------------------------
43 !
44 !++ Public type & procedure
45 !
46 type, extends(meshbase3d), public :: meshcubedspheredom3d
47 integer :: negx
48 integer :: negy
49 integer :: negz
50
51 real(rp), public :: xmin_gl, xmax_gl
52 real(rp), public :: ymin_gl, ymax_gl
53 real(rp), public :: zmin_gl, zmax_gl
54
55 real(rp), allocatable :: fz(:)
56
57 integer, allocatable :: rcdomijkp2lcmeshid(:,:,:,:)
58
59 real(rp) :: rplanet
60
61 type(meshcubedspheredom2d) :: mesh2d
62 type(quadrilateralelement) :: refelem2d
63
64 logical :: shallow_approx
65 contains
66 procedure :: init => meshcubedspheredom3d_init
67 procedure :: final => meshcubedspheredom3d_final
68 procedure :: generate => meshcubedspheredom3d_generate
69 procedure :: assigndomid => messhcubedspheredom3d_assigndomid
70 procedure :: getmesh2d => meshcubedspheredom3d_getmesh2d
71 procedure :: set_geometric_with_vcoord => meshcubedom3d_set_geometric_with_vcoord
73
74 !-----------------------------------------------------------------------------
75 !
76 !++ Public parameters & variables
77 !
78
79 !-----------------------------------------------------------------------------
80 !
81 !++ Private procedure
82 !
83
84 private :: meshcubedspheredom3d_calc_normal
85 private :: meshcubedspheredom3d_coord_conv
86 private :: meshcubedspheredom3d_set_metric
87 private :: fill_halo_metric
88
89 !-----------------------------------------------------------------------------
90 !
91 !++ Private parameters & variables
92 !
93
94contains
95!OCL SERIAL
96 subroutine meshcubedspheredom3d_init( this, &
97 NeGX, NeGY, NeGZ, RPlanet, &
98 dom_zmin, dom_zmax, &
99 refElem, NLocalMeshPerPrc, &
100 nproc, myrank, &
101 FZ, shallow_approx )
102
103 use scale_const, only: &
104 pi => const_pi
105 implicit none
106
107 class(meshcubedspheredom3d), intent(inout) :: this
108 integer, intent(in) :: NeGX
109 integer, intent(in) :: NeGY
110 integer, intent(in) :: NeGZ
111 real(RP), intent(in) :: RPlanet
112 real(RP), intent(in) :: dom_Zmin
113 real(RP), intent(in) :: dom_zmax
114 type(hexahedralelement), intent(in), target :: refElem
115 integer, intent(in) :: NLocalMeshPerPrc
116 integer, intent(in), optional :: nproc
117 integer, intent(in), optional :: myrank
118 real(RP), intent(in), optional :: FZ(NeGZ+1)
119 logical, intent(in), optional :: shallow_approx
120
121 integer :: k
122 real(RP) :: dz
123 !-----------------------------------------------------------------------------
124
125 this%NeGX = negx
126 this%NeGY = negy
127 this%NeGZ = negz
128
129 this%xmin_gl = - 0.25_rp * pi
130 this%xmax_gl = + 0.25_rp * pi
131 this%ymin_gl = - 0.25_rp * pi
132 this%ymax_gl = + 0.25_rp * pi
133 this%zmin_gl = dom_zmin
134 this%zmax_gl = dom_zmax
135 this%RPlanet = rplanet
136 this%dom_vol = 4.0_rp / 3.0_rp * pi * ( ( dom_zmax + rplanet )**3 - ( dom_zmin + rplanet )**3 )
137
138
139 !- Fz
140 allocate( this%FZ(this%NeGZ+1) )
141 if ( present(fz) ) then
142 this%FZ(:) = fz(:)
143 else
144 this%FZ(1 ) = dom_zmin
145 this%FZ(this%NeGZ+1) = dom_zmax
146 dz = (dom_zmax - dom_zmin) / dble(this%NeGZ)
147 do k=2, this%NeGZ
148 this%FZ(k) = this%FZ(k-1) + dz
149 end do
150 end if
151
152 !-
153 if ( present(shallow_approx) ) then
154 this%shallow_approx = shallow_approx
155 else
156 this%shallow_approx = .true.
157 end if
158
159 !--
160 call meshbase3d_init( this, refelem, nlocalmeshperprc, 6, &
161 nproc, myrank )
162
163 !---
164 call this%refElem2D%Init( this%refElem3D%PolyOrder_h, refelem%IsLumpedMatrix() )
165 call this%mesh2D%Init( negx, negy, rplanet, this%refElem2D, nlocalmeshperprc, &
166 nproc, myrank )
167
168 !-- Modify the information of dimension for the cubed sphere mesh
169 call this%SetDimInfo( meshbase3d_dimtypeid_x, "x", "1", "X-coordinate" )
170 call this%SetDimInfo( meshbase3d_dimtypeid_y, "y", "1", "Y-coordinate" )
171 call this%SetDimInfo( meshbase3d_dimtypeid_z, "z", "m", "Z-coordinate" )
172 call this%SetDimInfo( meshbase3d_dimtypeid_xyz, "xyz", "1", "XYZ-coordinate" )
173 call this%SetDimInfo( meshbase3d_dimtypeid_zt, "zt", "1", "XYZ-coordinate" )
174 call this%SetDimInfo( meshbase3d_dimtypeid_xyzt, "xyzt", "1", "XYZ-coordinate" )
175
176 return
177 end subroutine meshcubedspheredom3d_init
178
179!OCL SERIAL
180 subroutine meshcubedspheredom3d_final( this )
181 implicit none
182 class(meshcubedspheredom3d), intent(inout) :: this
183 !-----------------------------------------------------------------------------
184
185 if (this%isGenerated) then
186 if ( allocated(this%rcdomIJKP2LCMeshID) ) then
187 deallocate( this%rcdomIJKP2LCMeshID )
188 end if
189 else
190 if ( allocated( this%FZ ) ) deallocate( this%FZ )
191 end if
192
193 call this%mesh2D%Final()
194 call this%refElem2D%Final()
195
196 call meshbase3d_final( this )
197
198 return
199 end subroutine meshcubedspheredom3d_final
200
201!OCL SERIAL
202 subroutine meshcubedspheredom3d_getmesh2d( this, ptr_mesh2D )
203 implicit none
204 class(meshcubedspheredom3d), intent(in), target :: this
205 class(meshbase2d), pointer, intent(out) :: ptr_mesh2D
206 !-------------------------------------------------------
207
208 ptr_mesh2d => this%mesh2D
209 return
210 end subroutine meshcubedspheredom3d_getmesh2d
211
212!OCL SERIAL
213 subroutine meshcubedspheredom3d_generate( this )
214 use scale_mesh_cubedspheredom2d, only: &
216 implicit none
217
218 class(meshcubedspheredom3d), intent(inout), target :: this
219
220 integer :: n
221 type(localmesh3d), pointer :: mesh
222
223 integer :: tileID_table(this%LOCAL_MESH_NUM, this%PRC_NUM)
224 integer :: panelID_table(this%LOCAL_MESH_NUM*this%PRC_NUM)
225 integer :: pi_table(this%LOCAL_MESH_NUM*this%PRC_NUM)
226 integer :: pj_table(this%LOCAL_MESH_NUM*this%PRC_NUM)
227 integer :: pk_table(this%LOCAL_MESH_NUM*this%PRC_NUM)
228
229 integer :: NprcX_lc, NprcY_lc, NprcZ_lc
230 integer :: tileID
231 !-----------------------------------------------------------------------------
232
234 nprcx_lc, nprcy_lc, &
235 this%PRC_NUM, this%LOCAL_MESH_NUM_global, &
236 .true. )
237
238 nprcz_lc = 1
239
240 !--- Construct the connectivity of patches (only master node)
241
242 call this%AssignDomID( &
243 nprcx_lc, nprcy_lc, nprcz_lc, & ! (in)
244 tileid_table, panelid_table, & ! (out)
245 pi_table, pj_table, pk_table ) ! (out)
246
247 do n=1, this%LOCAL_MESH_NUM
248 mesh => this%lcmesh_list(n)
249 tileid = tileid_table(n, mesh%PRC_myrank+1)
250
251 call meshcubedspheredom3d_setuplocaldom( mesh, &
252 tileid, panelid_table(tileid), &
253 pi_table(tileid), pj_table(tileid), pk_table(tileid), &
254 nprcx_lc, nprcy_lc, nprcz_lc, &
255 this%xmin_gl, this%xmax_gl, this%ymin_gl, this%ymax_gl, &
256 this%zmin_gl, this%zmax_gl, this%RPlanet, &
257 this%NeGX/nprcx_lc, this%NeGY/nprcy_lc, this%NeGZ/nprcz_lc, &
258 this%FZ(:) )
259
260 call meshcubedspheredom2d_setuplocaldom( this%mesh2D%lcmesh_list(n), &
261 tileid, panelid_table(tileid), &
262 pi_table(tileid), pj_table(tileid), nprcx_lc, nprcy_lc, &
263 this%xmin_gl, this%xmax_gl, this%ymin_gl, this%ymax_gl, &
264 this%RPlanet, this%NeGX/nprcx_lc, this%NeGY/nprcy_lc )
265
266 call mesh%SetLocalMesh2D( this%mesh2D%lcmesh_list(n) )
267
268 !---
269 ! write(*,*) "** my_rank=", mesh%PRC_myrank
270 ! write(*,*) " tileID:", mesh%tileID
271 ! write(*,*) " pnlID:", mesh%panelID, "-- i,j (within a panel)=", pi_table(tileID), pj_table(tileID)
272 ! write(*,*) " local mesh:", n, "( total", this%LOCAL_MESH_NUM, ")"
273 ! write(*,*) " panel_connect:", this%tilePanelID_globalMap(:,mesh%tileID)
274 ! write(*,*) " tile_connect:", this%tileID_globalMap(:,mesh%tileID)
275 ! write(*,*) " face_connect:", this%tileFaceID_globalMap(:,mesh%tileID)
276 ! write(*,*) " domain size"
277 ! write(*,*) " NeX, NeY:", mesh%NeX, mesh%NeY
278 ! write(*,*) " [X], [Y]:", mesh%xmin, mesh%xmax, ":", mesh%ymin, mesh%ymax
279 end do
280
281 ! Set lon&lat position and metrics with the cubed sphere mesh
282 call meshcubedspheredom3d_set_metric( this )
283
284 ! To set rcdomIJP2LCMeshID, call AssignDomID for 2D mesh
285 call this%mesh2D%AssignDomID( &
286 nprcx_lc, nprcy_lc, & ! (in)
287 tileid_table, panelid_table, & ! (out)
288 pi_table, pj_table ) ! (out)
289
290 this%isGenerated = .true.
291 this%mesh2D%isGenerated = .true.
292
293 deallocate( this%FZ )
294
295 return
296 end subroutine meshcubedspheredom3d_generate
297
298!OCL SERIAL
299 subroutine meshcubedom3d_set_geometric_with_vcoord(this, lcdomID, GsqrtV_lc, zlev_lc, G13_lc, G23_lc)
300 implicit none
301 class(meshcubedspheredom3d), intent(inout), target :: this
302 integer, intent(in) :: lcdomID
303 real(RP), intent(in) :: GsqrtV_lc(this%refElem3D%Np,this%lcmesh_list(lcdomID)%NeA)
304 real(RP), intent(in) :: zlev_lc(this%refElem3D%Np,this%lcmesh_list(lcdomID)%NeA)
305 real(RP), intent(in) :: G13_lc(this%refElem3D%Np,this%lcmesh_list(lcdomID)%NeA)
306 real(RP), intent(in) :: G23_lc(this%refElem3D%Np,this%lcmesh_list(lcdomID)%NeA)
307
308 integer :: ke
309 class(localmesh3d), pointer :: lcmesh
310 !-------------------------------------------------------
311
312 lcmesh => this%lcmesh_list(lcdomid)
313
314 !$omp parallel private(ke)
315 !$omp do
316 do ke=lcmesh%NeS, lcmesh%NeE
317 lcmesh%zlev(:,ke) = zlev_lc(:,ke)
318 end do
319 !$omp do
320 do ke=lcmesh%NeS, lcmesh%NeA
321 if ( this%shallow_approx ) then
322 lcmesh%gam(:,ke) = 1.0_rp
323 else
324 lcmesh%gam(:,ke) = 1.0_rp + zlev_lc(:,ke) / this%RPlanet
325 end if
326
327 lcmesh%Gsqrt(:,ke) = gsqrtv_lc(:,ke) * lcmesh%gam(:,ke)**2 * lcmesh%Gsqrt(:,ke)
328 lcmesh%GI3(:,ke,1) = g13_lc(:,ke)
329 lcmesh%GI3(:,ke,2) = g23_lc(:,ke)
330 end do
331 !$omp end parallel
332
333 return
334 end subroutine meshcubedom3d_set_geometric_with_vcoord
335
336 !- private ------------------------------
337
338!OCL SERIAL
339 subroutine meshcubedspheredom3d_setuplocaldom( lcmesh, &
340 tileID, panelID, &
341 i, j, k, NprcX, NprcY, NprcZ, &
342 dom_xmin, dom_xmax, dom_ymin, dom_ymax, dom_zmin, dom_zmax, &
343 planet_radius, NeX, NeY, NeZ, &
344 FZ )
345
347 meshutilcubedsphere3d_genconnectivity, &
348 meshutilcubedsphere3d_gencubedomain, &
349 meshutilcubedsphere3d_buildinteriormap, &
350 meshutilcubedsphere3d_genpatchboundarymap
351
353
354 implicit none
355
356 type(localmesh3d), intent(inout) :: lcmesh
357 integer, intent(in) :: tileID
358 integer, intent(in) :: panelID
359 integer, intent(in) :: i, j, k
360 integer, intent(in) :: NprcX, NprcY, NprcZ
361 real(RP), intent(in) :: dom_xmin, dom_xmax
362 real(RP), intent(in) :: dom_ymin, dom_ymax
363 real(RP), intent(in) :: dom_zmin, dom_zmax
364 real(RP), intent(in) :: planet_radius
365 integer, intent(in) :: NeX, NeY, NeZ
366 real(RP), intent(in) :: FZ(NeZ*NprcZ+1)
367
368 class(elementbase3d), pointer :: elem
369 real(RP) :: delx, dely
370 real(RP) :: FZ_lc(NeZ+1)
371
372 integer :: ii, jj, kk
373 integer :: ke
374 !-----------------------------------------------------------------------------
375
376 elem => lcmesh%refElem3D
377 lcmesh%tileID = tileid
378 lcmesh%panelID = panelid
379
380 !--
381 lcmesh%Ne = nex * ney * nez
382 lcmesh%Nv = (nex + 1)*(ney + 1)*(nez + 1)
383 lcmesh%NeS = 1
384 lcmesh%NeE = lcmesh%Ne
385 lcmesh%NeA = lcmesh%Ne + 2*(nex + ney)*nez + 2*nex*ney
386
387 lcmesh%NeX = nex
388 lcmesh%NeY = ney
389 lcmesh%NeZ = nez
390
391 lcmesh%Ne2D = nex * ney
392 lcmesh%Ne2DA = nex * ney + 2*(nex + ney)
393
394 !--
395 delx = ( dom_xmax - dom_xmin ) / dble(nprcx)
396 dely = ( dom_ymax - dom_ymin ) / dble(nprcy)
397 fz_lc(:) = fz((k-1)*nez+1:k*nez+1)
398 lcmesh%xmin = dom_xmin + (i-1)*delx
399 lcmesh%xmax = dom_xmin + i *delx
400 lcmesh%ymin = dom_ymin + (j-1)*dely
401 lcmesh%ymax = dom_ymin + j *dely
402 lcmesh%zmin = fz_lc(1)
403 lcmesh%zmax = fz_lc(nez+1)
404
405 !--
406 allocate( lcmesh%pos_ev(lcmesh%Nv,3) )
407 allocate( lcmesh%EToV(lcmesh%Ne,elem%Nv) )
408 allocate( lcmesh%EToE(lcmesh%Ne,elem%Nfaces) )
409 allocate( lcmesh%EToF(lcmesh%Ne,elem%Nfaces) )
410 allocate( lcmesh%BCType(lcmesh%refElem%Nfaces,lcmesh%Ne) )
411 allocate( lcmesh%VMapM(elem%NfpTot, lcmesh%Ne) )
412 allocate( lcmesh%VMapP(elem%NfpTot, lcmesh%Ne) )
413 allocate( lcmesh%MapM(elem%NfpTot, lcmesh%Ne) )
414 allocate( lcmesh%MapP(elem%NfpTot, lcmesh%Ne) )
415
416 allocate( lcmesh%EMap3Dto2D(lcmesh%Ne) )
417
418 lcmesh%BCType(:,:) = bctype_interior
419
420 !----
421 call meshutilcubedsphere3d_gencubedomain( lcmesh%pos_ev, lcmesh%EToV, & ! (out)
422 lcmesh%NeX, lcmesh%xmin, lcmesh%xmax, & ! (in)
423 lcmesh%NeY, lcmesh%ymin, lcmesh%ymax, & ! (in)
424 lcmesh%NeZ, lcmesh%zmin, lcmesh%zmax, fz=fz_lc ) ! (in)
425
426 !---
427 call meshbase3d_setgeometricinfo(lcmesh, meshcubedspheredom3d_coord_conv, meshcubedspheredom3d_calc_normal )
428
429 !---
430 call meshutilcubedsphere3d_genconnectivity( lcmesh%EToE, lcmesh%EToF, & ! (out)
431 lcmesh%EToV, lcmesh%Ne, elem%Nfaces ) ! (in)
432
433 !---
434 call meshutilcubedsphere3d_buildinteriormap( lcmesh%VmapM, lcmesh%VMapP, lcmesh%MapM, lcmesh%MapP, & ! (out)
435 lcmesh%pos_en, lcmesh%pos_ev, lcmesh%EToE, lcmesh%EtoF, lcmesh%EtoV, & ! (in)
436 elem%Fmask_h, elem%Fmask_v, lcmesh%Ne, lcmesh%Nv, elem%Np, elem%Nfp_h, elem%Nfp_v, elem%NfpTot, & ! (in)
437 elem%Nfaces_h, elem%Nfaces_v, elem%Nfaces )
438
439
440 call meshutilcubedsphere3d_genpatchboundarymap( lcmesh%VMapB, lcmesh%MapB, lcmesh%VMapP, & !(out)
441 lcmesh%pos_en, lcmesh%xmin, lcmesh%xmax, lcmesh%ymin, lcmesh%ymax, lcmesh%zmin, lcmesh%zmax, & ! (in)
442 elem%Fmask_h, elem%Fmask_v, lcmesh%Ne, lcmesh%Nv, elem%Np, elem%Nfp_h, elem%Nfp_v, elem%NfpTot, & ! (in)
443 elem%Nfaces_h, elem%Nfaces_v, elem%Nfaces )
444
445 !---
446 !$omp parallel do collapse(2) private(ii,ke)
447 do kk=1, lcmesh%NeZ
448 do jj=1, lcmesh%NeY
449 do ii=1, lcmesh%NeX
450 ke = ii + (jj-1) * lcmesh%NeX + (kk-1) * lcmesh%NeX * lcmesh%NeY
451 lcmesh%EMap3Dto2D(ke) = ii + (jj-1) * lcmesh%NeX
452 end do
453 end do
454 end do
455
456 return
457 end subroutine meshcubedspheredom3d_setuplocaldom
458
459!OCL SERIAL
460 subroutine messhcubedspheredom3d_assigndomid( this, &
461 NprcX_lc, NprcY_lc, NprcZ_lc, &
462 tileID_table, panelID_table, &
463 pi_table, pj_table, pk_table )
464
465 use scale_meshutil_cubedsphere3d, only: &
467
468 implicit none
469
470 class(meshcubedspheredom3d), target, intent(inout) :: this
471 integer, intent(in) :: NprcX_lc
472 integer, intent(in) :: NprcY_lc
473 integer, intent(in) :: NprcZ_lc
474 integer, intent(out) :: tileID_table(this%LOCAL_MESH_NUM, this%PRC_NUM)
475 integer, intent(out) :: panelID_table(this%LOCAL_MESH_NUM*this%PRC_NUM)
476 integer, intent(out) :: pi_table(this%LOCAL_MESH_NUM*this%PRC_NUM)
477 integer, intent(out) :: pj_table(this%LOCAL_MESH_NUM*this%PRC_NUM)
478 integer, intent(out) :: pk_table(this%LOCAL_MESH_NUM*this%PRC_NUM)
479
480 integer :: n
481 integer :: prc
482 integer :: tileID
483 integer :: is_lc, js_lc, ks_lc, ps_lc
484 integer :: ilc_count, jlc_count, klc_count, plc_count
485 integer :: ilc, jlc, klc, plc
486
487 type(localmesh3d), pointer :: lcmesh
488 !-----------------------------------------------------------------------------
489
491 panelid_table, pi_table, pj_table, pk_table, & ! (out)
492 this%tileID_globalMap, this%tileFaceID_globalMap, this%tilePanelID_globalMap, & ! (out)
493 this%LOCAL_MESH_NUM_global, nprcz_lc ) ! (in)
494
495 !----
496
497 do prc=1, this%PRC_NUM
498 do n=1, this%LOCAL_MESH_NUM
499 tileid = n + (prc-1)*this%LOCAL_MESH_NUM
500 lcmesh => this%lcmesh_list(n)
501
502 !-
503 tileid_table(n,prc) = tileid
504 this%tileID_global2localMap(tileid) = n
505 this%PRCRank_globalMap(tileid) = prc - 1
506
507 !-
508 if ( this%PRCRank_globalMap(tileid) == lcmesh%PRC_myrank ) then
509 if (n==1) then
510 is_lc = pi_table(tileid); ilc_count = 1
511 js_lc = pj_table(tileid); jlc_count = 1
512 ks_lc = pk_table(tileid); klc_count = 1
513 ps_lc = panelid_table(tileid); plc_count = 1
514 end if
515 if(is_lc < pi_table(tileid)) ilc_count = ilc_count + 1
516 if(js_lc < pj_table(tileid)) jlc_count = jlc_count + 1
517 if(ks_lc < pk_table(tileid)) klc_count = klc_count + 1
518 if(ps_lc < panelid_table(tileid)) plc_count = plc_count + 1
519 end if
520 end do
521 end do
522
523 allocate( this%rcdomIJKP2LCMeshID(ilc_count,jlc_count,klc_count,plc_count) )
524 do plc=1, plc_count
525 do klc=1, klc_count
526 do jlc=1, jlc_count
527 do ilc=1, ilc_count
528 this%rcdomIJKP2LCMeshID(ilc,jlc,klc,plc) = ilc + (jlc - 1)*ilc_count + (klc - 1)*ilc_count*jlc_count &
529 + (plc-1)*ilc_count*jlc_count*klc_count
530 end do
531 end do
532 end do
533 end do
534
535 return
536 end subroutine messhcubedspheredom3d_assigndomid
537
538!OCL SERIAL
539 subroutine meshcubedspheredom3d_coord_conv( x, y, z, xX, xY, xZ, yX, yY, yZ, zX, zY, zZ, &
540 vx, vy, vz, elem )
541
542 implicit none
543
544 type(elementbase3d), intent(in) :: elem
545 real(RP), intent(out) :: x(elem%Np), y(elem%Np), z(elem%Np)
546 real(RP), intent(out) :: xX(elem%Np), xY(elem%Np), xZ(elem%Np)
547 real(RP), intent(out) :: yX(elem%Np), yY(elem%Np), yZ(elem%Np)
548 real(RP), intent(out) :: zX(elem%Np), zY(elem%Np), zZ(elem%Np)
549 real(RP), intent(in) :: vx(elem%Nv), vy(elem%Nv), vz(elem%Nv)
550
551 !-------------------------------------------------
552
553 x(:) = vx(1) + 0.5_rp*(elem%x1(:) + 1.0_rp)*(vx(2) - vx(1))
554 y(:) = vy(1) + 0.5_rp*(elem%x2(:) + 1.0_rp)*(vy(3) - vy(1))
555 z(:) = vz(1) + 0.5_rp*(elem%x3(:) + 1.0_rp)*(vz(5) - vz(1))
556
557 xx(:) = 0.5_rp*(vx(2) - vx(1)) !matmul(refElem%Dx1,mesh%x1(:,n))
558 xy(:) = 0.0_rp !matmul(refElem%Dx2,mesh%x1(:,n))
559 xz(:) = 0.0_rp !matmul(refElem%Dx3,mesh%x1(:,n))
560 yx(:) = 0.0_rp !matmul(refElem%Dx1,mesh%x2(:,n))
561 yy(:) = 0.5_rp*(vy(3) - vy(1)) !matmul(refElem%Dx2,mesh%x2(:,n))
562 yz(:) = 0.0_rp !matmul(refElem%Dx3,mesh%x2(:,n))
563 zx(:) = 0.0_rp !matmul(refElem%Dx1,mesh%x3(:,n))
564 zy(:) = 0.0_rp !matmul(refElem%Dx2,mesh%x3(:,n))
565 zz(:) = 0.5_rp*(vz(5) - vz(1)) !matmul(refElem%Dx3,mesh%x3(:,n))
566
567 return
568 end subroutine meshcubedspheredom3d_coord_conv
569
570!OCL SERIAL
571 subroutine meshcubedspheredom3d_calc_normal( normal_fn, &
572 Escale_f, fid_h, fid_v, elem )
573
574 implicit none
575
576 type(elementbase3d), intent(in) :: elem
577 real(RP), intent(out) :: normal_fn(elem%NfpTot,3)
578 integer, intent(in) :: fid_h(elem%Nfp_h,elem%Nfaces_h)
579 integer, intent(in) :: fid_v(elem%Nfp_v,elem%Nfaces_v)
580 real(RP), intent(in) :: Escale_f(elem%NfpTot,3,3)
581
582 integer :: d
583 !-------------------------------------------------
584
585 do d=1, 3
586 normal_fn(fid_h(:,1),d) = - escale_f(fid_h(:,1),2,d)
587 normal_fn(fid_h(:,2),d) = + escale_f(fid_h(:,2),1,d)
588 normal_fn(fid_h(:,3),d) = + escale_f(fid_h(:,3),2,d)
589 normal_fn(fid_h(:,4),d) = - escale_f(fid_h(:,4),1,d)
590
591 normal_fn(fid_v(:,1),d) = - escale_f(fid_v(:,1),3,d)
592 normal_fn(fid_v(:,2),d) = + escale_f(fid_v(:,2),3,d)
593 end do
594
595 return
596 end subroutine meshcubedspheredom3d_calc_normal
597
598 !--
599
600!OCL SERIAL
601 subroutine meshcubedspheredom3d_set_metric( this )
602 use scale_cubedsphere_coord_cnv, only: &
605
606 implicit none
607 class(meshcubedspheredom3d), intent(inout), target :: this
608
609 integer :: n
610 integer :: ke, ke2D
611
612 class(localmesh3d), pointer :: lcmesh
613 class(localmesh2d), pointer :: lcmesh2D
614 class(elementbase2d), pointer :: elem2D
615
616 real(RP), allocatable :: gam2D(:,:)
617 !----------------------------------------------------
618
619 do n=1, this%mesh2D%LOCAL_MESH_NUM
620 lcmesh => this%lcmesh_list(n)
621 lcmesh2d => this%mesh2D%lcmesh_list(n)
622 elem2d => lcmesh2d%refElem2D
623
624 allocate( gam2d(elem2d%Np,lcmesh2d%Ne) )
625 gam2d(:,:) = 1.0_rp
626
628 lcmesh2d%panelID, lcmesh2d%pos_en(:,:,1), lcmesh2d%pos_en(:,:,2), gam2d(:,:), & ! (in)
629 lcmesh2d%Ne * elem2d%Np, & ! (in)
630 lcmesh%lon2D(:,:), lcmesh%lat2D(:,:) ) ! (out)
631
633 lcmesh2d%pos_en(:,:,1), lcmesh2d%pos_en(:,:,2), elem2d%Np * lcmesh2d%Ne, this%RPlanet, & ! (in)
634 lcmesh%G_ij, lcmesh%GIJ, lcmesh%GsqrtH ) ! (out)
635
636 !$omp parallel do private(ke2D)
637 do ke=lcmesh%NeS, lcmesh%NeE
638 ke2d = lcmesh%EMap3Dto2D(ke)
639
640 if ( this%shallow_approx ) then
641 lcmesh%gam(:,ke) = 1.0_rp
642 else
643 lcmesh%gam(:,ke) = 1.0_rp + lcmesh%pos_en(:,ke,3) / this%RPlanet
644 end if
645 lcmesh%Gsqrt(:,ke) = lcmesh%GsqrtH(lcmesh%refElem3D%IndexH2Dto3D(:),ke2d)
646 end do
647
648 call fill_halo_metric( lcmesh%Gsqrt, lcmesh%gam, lcmesh%VMapM, lcmesh%VMapP, lcmesh, lcmesh%refElem3D )
649
650 deallocate( gam2d )
651 !--
652 end do
653
654
655 return
656 end subroutine meshcubedspheredom3d_set_metric
657
658!OCL SERIAL
659 subroutine fill_halo_metric( Gsqrt, gam, vmapM, vmapP, lmesh, elem )
660 implicit none
661 class(localmesh3d), intent(in) :: lmesh
662 class(elementbase3d), intent(in) :: elem
663 integer, intent(in) :: vmapM(elem%NfpTot*lmesh%Ne)
664 integer, intent(in) :: vmapP(elem%NfpTot*lmesh%Ne)
665 real(RP), intent(inout) :: Gsqrt(elem%Np*lmesh%NeA)
666 real(RP), intent(inout) :: gam(elem%Np*lmesh%NeA)
667
668 integer :: i, iM, iP
669 !------------------------------------------------
670
671 !$omp parallel do private(i, iM, iP)
672 do i=1, elem%NfpTot*lmesh%Ne
673 im = vmapm(i); ip = vmapp(i)
674 if ( ip > elem%Np * lmesh%Ne ) then
675 gsqrt(ip) = gsqrt(im)
676 gam(ip) = gam(im)
677 end if
678 end do
679 return
680 end subroutine fill_halo_metric
681
682end module scale_mesh_cubedspheredom3d
module common / Coordinate conversion with a cubed-sphere
subroutine, public cubedspherecoordcnv_cs2lonlatpos(panelid, alpha, beta, gam, np, lon, lat)
subroutine, public cubedspherecoordcnv_getmetric(alpha, beta, np, radius, g_ij, gij, gsqrt)
module FElib / Element / Base
module FElib / Element / hexahedron
module FElib / Element / Quadrilateral
module FElib / Mesh / Local 2D
module FElib / Mesh / Local 3D
module FElib / Mesh / Local, Base
integer, parameter, public bctype_interior
module FElib / Mesh / Base 2D
subroutine, public meshbase2d_final(this)
subroutine, public meshbase2d_init(this, refelem, nlocalmeshperprc, nprocs, myrank)
subroutine, public meshbase2d_setgeometricinfo(lcmesh, coord_conv, calc_normal)
module FElib / Mesh / Base 3D
subroutine, public meshbase3d_init(this, refelem, nlocalmeshperprc, nsidetile, nproc, myrank)
integer, public meshbase3d_dimtypeid_y
integer, public meshbase3d_dimtypeid_zt
integer, public meshbase3d_dimtypeid_z
integer, public meshbase3d_dimtype_num
subroutine, public meshbase3d_final(this)
subroutine, public meshbase3d_setgeometricinfo(lcmesh, coord_conv, calc_normal)
integer, public meshbase3d_dimtypeid_xyz
integer, public meshbase3d_dimtypeid_x
integer, public meshbase3d_dimtypeid_xyzt
module FElib / Mesh / Cubed-sphere 2D domain
subroutine, public meshcubedspheredom2d_check_division_params(nprcx_lc, nprcy_lc, prc_num, local_mesh_num_global, call_prc_abort)
subroutine, public meshcubedspheredom2d_setuplocaldom(lcmesh, tileid, panelid, i, j, nprcx, nprcy, dom_xmin, dom_xmax, dom_ymin, dom_ymax, planet_radius, nex, ney)
module FElib / Mesh / Cubed-sphere 3D domain
subroutine meshcubedspheredom3d_init(this, negx, negy, negz, rplanet, dom_zmin, dom_zmax, refelem, nlocalmeshperprc, nproc, myrank, fz, shallow_approx)
module FElib / Mesh / utility for 3D cubed-sphere mesh
subroutine, public meshutilcubedsphere3d_buildglobalmap(panelid_table, pi_table, pj_table, pk_table, tileid_map, tilefaceid_map, tilepanelid_map, ntile, nez)