5 integer, parameter::msize
=14
6 integer, parameter::max_levels
=5
10 real:: minaspect
=1./3.,maxaspect
=3.
11 real:: A(3,3)=reshape((/1., 0., 0., 0., 1., 0., 0., 0., 1./),(/3, 3/))
12 integer:: coarsest_iter
=100 ! to solve the coarse problem
13 integer:: maxit
=50 ! total iterations
14 integer:: nsmooth
=3 ! smoothing iterations before correction
15 integer:: nsmooth_coarse
=2 ! smoothing iterations on coarse levels
16 integer:: maxit_coarse
=8 ! on levels>1: 2 smoothing, coarse, 2 smoothing, coarse, 2 smoothing
17 integer:: debug_level
=-1 ! multigrid level to debug up to
18 integer:: msglevel
=1 ! type of messages to print
19 integer:: print_level
=2 ! multigrid level to print messages up to
20 !logical:: check_relres=.true. ! check residual after every base iteration if to continue
21 logical:: check_relres
=.false
.
22 real:: restol
=1e-6 ! residual tolerance to stop iterating
23 !logical:: check_reldif=.false. ! check difference after every base iteration if to continue
24 logical:: check_reldif
=.true
. ! check difference after every base iteration if to continue
25 real:: diftol_finest
=1e-6 ! keep iterating while iterates change by this
26 real:: diftol_coarse
=1e-1 ! keep iterating while iterates change by this on corse levels
27 real:: diftol_coarsest
=1e-2 ! keep iterating while iterates change by this on corsest level
30 type(params_type
)::params
35 real, dimension(3,3):: A
! penalty weight matrix
36 real, pointer, dimension(:,:,:):: X
, Y
, Z
! grid vertices
37 real, pointer, dimension(:,:,:):: & !
38 f
, lambda
, res
! multigrid variables
40 real, pointer, dimension(:,:,:,:):: Kglo
! global stiffness matrix
42 real:: dx
,dy
! horizontal spacing, scalar
43 real, pointer, dimension(:)::dz
! vertical spacing of the layers
44 integer::nx
,ny
,nz
,nn
! mesh size in terms of vertices
48 integer:: cr_x
, cr_y
! coarsening factors
49 integer, pointer, dimension(:):: icl_x
, icl_y
, icl_z
! coarsening indices
53 type(mg_type
):: mg(max_levels
+1) ! the main multigrid structure
57 subroutine allocate_mg_level(mg
) !allocate one multigrid level
58 type(mg_type
),intent(inout
)::mg
!multigrid structure
61 ifds
, ifde
, kfds
, kfde
, jfds
, jfde
, & ! fire grid dimensions
62 ifms
, ifme
, kfms
, kfme
, jfms
, jfme
, & ! memory dimensions
63 ifps
, ifpe
, kfps
, kfpe
, jfps
, jfpe
, & ! fire patch bounds
64 ifts
, ifte
, kfts
, kfte
, jfts
, jfte
! tile dimensions
67 call get_mg_dims(mg
, &
68 ifds
, ifde
, kfds
,kfde
, jfds
, jfde
, & ! fire grid dimensions
69 ifms
, ifme
, kfms
,kfme
, jfms
, jfme
, &
70 ifps
, ifpe
, kfps
,kfpe
, jfps
, jfpe
, & ! fire patch bounds
71 ifts
, ifte
, kfts
,kfte
, jfts
,jfte
)
73 if (.not
.associated(mg
%X
))allocate(mg
%X(ifms
: ifme
, kfms
: kfme
, jfms
: jfme
))
74 if (.not
.associated(mg
%Y
))allocate(mg
%Y(ifms
: ifme
, kfms
: kfme
, jfms
: jfme
))
75 if (.not
.associated(mg
%Z
))allocate(mg
%Z(ifms
: ifme
, kfms
: kfme
, jfms
: jfme
))
76 allocate(mg
%F(ifms
: ifme
, kfms
: kfme
, jfms
: jfme
))
77 allocate(mg
%lambda(ifms
: ifme
, kfms
: kfme
, jfms
: jfme
))
78 allocate(mg
%res(ifms
: ifme
, kfms
: kfme
, jfms
: jfme
))
80 end subroutine allocate_mg_level
82 subroutine get_mg_dims(mg_level
, &
83 ifds
, ifde
, kfds
, kfde
, jfds
, jfde
, & ! fire grid dimensions
84 ifms
, ifme
, kfms
, kfme
, jfms
, jfme
, & ! memory dimensions
85 ifps
, ifpe
, kfps
, kfpe
, jfps
, jfpe
, & ! fire patch bounds
86 ifts
, ifte
, kfts
, kfte
, jfts
, jfte
) ! tile dimensions
88 type(mg_type
),intent(in
)::mg_level
89 integer, intent(out
):: &
90 ifds
, ifde
, kfds
, kfde
, jfds
, jfde
, & ! fire grid dimensions
91 ifms
, ifme
, kfms
, kfme
, jfms
, jfme
, & ! memory dimensions
92 ifps
, ifpe
, kfps
, kfpe
, jfps
, jfpe
, & ! fire patch bounds
93 ifts
, ifte
, kfts
, kfte
, jfts
, jfte
! tile dimensions
94 character(len
=256)::msg
97 ifde
= mg_level
%nx
-1 ! dimension in elements
118 ifme
= ifpe
+ 2 ! need +1 for vertex grid, and +1 for zero strip
123 write(msg
,*)"get_mg_dims: domain",ifds
, ifde
, kfds
, kfde
, jfds
, jfde
125 write(msg
,*)"get_mg_dims: memory",ifms
, ifme
, kfms
, kfme
, jfms
, jfme
127 write(msg
,*)"get_mg_dims: patch ",ifps
, ifde
, kfps
, kfpe
, jfps
, jfpe
129 write(msg
,*)"get_mg_dims: tile ",ifts
, ifte
, kfts
, kfte
, jfts
, jfte
132 end subroutine get_mg_dims
134 subroutine write_3d(mg
,l
,var
,name
,v
)
135 ! write array in text file for debugging
139 type(mg_type
),intent(in
)::mg(:) !multigrid structure
140 integer,intent(in
)::l
!level
141 real, intent(in
)::var(:,:,:) !the array
142 character(len
=*),intent(in
)::name
143 character(len
=1),intent(in
)::v
!'v' or 'e'
147 ifds
, ifde
, kfds
, kfde
, jfds
, jfde
, & ! fire grid dimensions
148 ifms
, ifme
, kfms
, kfme
, jfms
, jfme
, & ! memory dimensions
149 ifps
, ifpe
, kfps
, kfpe
, jfps
, jfpe
, & ! fire patch bounds
150 ifts
, ifte
, kfts
, kfte
, jfts
, jfte
! tile dimensions
156 call get_mg_dims(mg(l
), &
157 ifds
, ifde
, kfds
,kfde
, jfds
, jfde
, & ! fire grid dimensions
158 ifms
, ifme
, kfms
,kfme
, jfms
, jfme
, &
159 ifps
, ifpe
, kfps
,kfpe
, jfps
, jfpe
, & ! fire patch bounds
160 ifts
, ifte
, kfts
,kfte
, jfts
,jfte
)
165 ie
= snode(ifte
,ifde
,+1) ! vertex based
166 je
= snode(jfte
,jfde
,+1)
167 ke
= snode(kfte
,kfde
,+1)
173 call crash('write_3d: bad v')
176 call write_tight(var
) ! write dereferenced
180 subroutine write_tight(varr
)
181 real, intent(in
)::varr(ifms
:ifme
,kfms
:kfme
,jfms
:jfme
)
182 ! for element/cell/midpoint based arrays, like fmw winds
183 ! open(iu,file='varr.dat',form='unformatted',status='unknown')
184 ! write(iu)varr(ifts:ifte,kfts:kfte,jfts:jfte)
186 call write_array(varr(ifts
:ie
,kfts
:ke
,jfts
:je
),name
//lc
)
187 end subroutine write_tight
189 end subroutine write_3d
191 subroutine print_mg_dims(mg
,l
)
192 type(mg_type
),intent(in
)::mg(:) ! multigrid level
193 print *,'level ',mg(l
)%level
194 if(associated(mg(l
)%X
))print *,'X memory shape ',shape(mg(l
)%X
)
195 if(associated(mg(l
)%Y
))print *,'Y memory shape ',shape(mg(l
)%Y
)
196 if(associated(mg(l
)%Z
))print *,'Z memory shape ',shape(mg(l
)%Z
)
197 print *,'grid size nx=',mg(l
)%nx
,' ny=',mg(l
)%ny
,' nz=',mg(l
)%nz
, &
198 ' total ndof=',mg(l
)%nn
199 print *,'dx=',mg(l
)%dx
,' dy=',mg(l
)%dy
200 if(associated(mg(l
)%dz
))then
201 print *,'dz shape',shape(mg(l
)%dz
)
202 if(product(shape(mg(l
)%dz
))>0) then
203 print *,'size ',size(mg(l
)%dz
)
204 print *,'dz=',mg(l
)%dz
207 end subroutine print_mg_dims
209 end module module_common