/[MITgcm]/MITgcm/pkg/generic_advdiff/gad_implicit_r.F
ViewVC logotype

Contents of /MITgcm/pkg/generic_advdiff/gad_implicit_r.F

Parent Directory Parent Directory | Revision Log Revision Log | View Revision Graph Revision Graph


Revision 1.14 - (show annotations) (download)
Fri Jun 26 23:10:09 2009 UTC (14 years, 10 months ago) by jahn
Branch: MAIN
CVS Tags: checkpoint63d, checkpoint63e, checkpoint63f, checkpoint63a, checkpoint63b, checkpoint63c, checkpoint62, checkpoint63, checkpoint62c, checkpoint62b, checkpoint62a, checkpoint62g, checkpoint62f, checkpoint62e, checkpoint62d, checkpoint62k, checkpoint62j, checkpoint62i, checkpoint62h, checkpoint62o, checkpoint62n, checkpoint62m, checkpoint62l, checkpoint62s, checkpoint62r, checkpoint62q, checkpoint62p, checkpoint62w, checkpoint62v, checkpoint62u, checkpoint62t, checkpoint62z, checkpoint62y, checkpoint62x, checkpoint61v, checkpoint61w, checkpoint61t, checkpoint61u, checkpoint61s, checkpoint61z, checkpoint61x, checkpoint61y
Changes since 1.13: +11 -9 lines
add package longstep

1 C $Header: /u/gcmpack/MITgcm/pkg/generic_advdiff/gad_implicit_r.F,v 1.13 2006/06/18 23:27:44 jmc Exp $
2 C $Name: $
3
4 #include "GAD_OPTIONS.h"
5
6 CBOP
7 C !ROUTINE: GAD_IMPLICIT_R
8 C !INTERFACE:
9 SUBROUTINE GAD_IMPLICIT_R(
10 I implicitAdvection, advectionScheme, tracerIdentity,
11 I deltaTLev,
12 I kappaRX, wVel, tracer,
13 U gTracer,
14 I bi, bj, myTime, myIter, myThid )
15 C !DESCRIPTION:
16 C Solve implicitly vertical advection and diffusion for one tracer.
17
18 C !USES:
19 IMPLICIT NONE
20 C == Global data ==
21 #include "SIZE.h"
22 #include "EEPARAMS.h"
23 #include "PARAMS.h"
24 #include "GRID.h"
25 #include "GAD.h"
26
27 C !INPUT/OUTPUT PARAMETERS:
28 C == Routine Arguments ==
29 C implicitAdvection :: if True, treat vertical advection implicitly
30 C advectionScheme :: advection scheme to use
31 C tracerIdentity :: Identifier for the tracer
32 C kappaRX :: 3-D array for vertical diffusion coefficient
33 C wVel :: vertical component of the velcity field
34 C tracer :: tracer field at current time step
35 C gTracer :: future tracer field
36 C bi,bj :: tile indices
37 C myTime :: current time
38 C myIter :: current iteration number
39 C myThid :: thread number
40 LOGICAL implicitAdvection
41 INTEGER advectionScheme
42 INTEGER tracerIdentity
43 _RL deltaTLev(Nr)
44 _RL kappaRX(1-Olx:sNx+Olx,1-Oly:sNy+Oly,Nr)
45 _RL wVel (1-Olx:sNx+Olx,1-Oly:sNy+Oly,Nr,nSx,nSy)
46 _RL tracer (1-Olx:sNx+Olx,1-Oly:sNy+Oly,Nr,nSx,nSy)
47 _RL gTracer(1-Olx:sNx+Olx,1-Oly:sNy+Oly,Nr,nSx,nSy)
48 INTEGER bi, bj
49 _RL myTime
50 INTEGER myIter, myThid
51
52 C !LOCAL VARIABLES:
53 C == Local variables ==
54 C iMin,iMax,jMin,jMax :: computational domain
55 C i,j,k :: loop indices
56 C a5d :: 2nd lower diagonal of the pentadiagonal matrix
57 C b5d :: 1rst lower diagonal of the pentadiagonal matrix
58 C c5d :: main diagonal of the pentadiagonal matrix
59 C d5d :: 1rst upper diagonal of the pentadiagonal matrix
60 C e5d :: 2nd upper diagonal of the pentadiagonal matrix
61 C rTrans :: vertical volume transport at inteface k
62 C rTransKp1 :: vertical volume transport at inteface k+1
63 C localTijk :: local copy of tracer (for Non-Lin Adv.Scheme)
64 C diagonalNumber :: number of non-zero diagonals in the matrix
65 C errCode :: > 0 if singular matrix
66 INTEGER iMin,iMax,jMin,jMax
67 INTEGER i,j,k
68 INTEGER diagonalNumber, errCode
69 _RL a5d(1-Olx:sNx+Olx,1-Oly:sNy+Oly,Nr)
70 _RL b5d(1-Olx:sNx+Olx,1-Oly:sNy+Oly,Nr)
71 _RL c5d(1-Olx:sNx+Olx,1-Oly:sNy+Oly,Nr)
72 _RL d5d(1-Olx:sNx+Olx,1-Oly:sNy+Oly,Nr)
73 _RL e5d(1-Olx:sNx+Olx,1-Oly:sNy+Oly,Nr)
74 _RL wFld (1-Olx:sNx+Olx,1-Oly:sNy+Oly)
75 _RL rTrans (1-Olx:sNx+Olx,1-Oly:sNy+Oly)
76 _RL rTransKp1(1-Olx:sNx+Olx,1-Oly:sNy+Oly)
77 _RL localTijk(1-Olx:sNx+Olx,1-Oly:sNy+Oly,Nr)
78 #ifdef ALLOW_DIAGNOSTICS
79 CHARACTER*8 diagName
80 CHARACTER*4 GAD_DIAG_SUFX, diagSufx
81 EXTERNAL GAD_DIAG_SUFX
82 LOGICAL DIAGNOSTICS_IS_ON
83 EXTERNAL DIAGNOSTICS_IS_ON
84 _RL df (1-Olx:sNx+Olx,1-Oly:sNy+Oly)
85 #endif
86 CEOP
87
88 C-- no need to solve anything with only 1 level:
89 IF (Nr.GT.1) THEN
90
91 C-- Initialise
92 iMin = 1
93 jMin = 1
94 iMax = sNx
95 jMax = sNy
96 DO k=1,Nr
97 DO j=1-Oly,sNy+Oly
98 DO i=1-Olx,sNx+Olx
99 a5d(i,j,k) = 0. _d 0
100 b5d(i,j,k) = 0. _d 0
101 c5d(i,j,k) = 1. _d 0
102 d5d(i,j,k) = 0. _d 0
103 e5d(i,j,k) = 0. _d 0
104 ENDDO
105 ENDDO
106 ENDDO
107 diagonalNumber = 1
108
109 C-- Non-Linear Advection scheme: keep a local copy of tracer field
110 IF ( advectionScheme.EQ.ENUM_FLUX_LIMIT .OR.
111 & advectionScheme.EQ.ENUM_DST3_FLUX_LIMIT ) THEN
112 IF ( multiDimAdvection ) THEN
113 DO k=1,Nr
114 DO j=1-Oly,sNy+Oly
115 DO i=1-Olx,sNx+Olx
116 localTijk(i,j,k) = gTracer(i,j,k,bi,bj)
117 ENDDO
118 ENDDO
119 ENDDO
120 ELSE
121 DO k=1,Nr
122 DO j=1-Oly,sNy+Oly
123 DO i=1-Olx,sNx+Olx
124 localTijk(i,j,k) = tracer(i,j,k,bi,bj)
125 ENDDO
126 ENDDO
127 ENDDO
128 ENDIF
129 ENDIF
130
131 IF (implicitDiffusion) THEN
132 C-- set the tri-diagonal matrix to solve the implicit diffusion problem
133 diagonalNumber = 3
134 C- 1rst lower diagonal :
135 DO k=2,Nr
136 DO j=jMin,jMax
137 DO i=iMin,iMax
138 b5d(i,j,k) = -deltaTLev(k)*maskC(i,j,k-1,bi,bj)
139 & *_recip_hFacC(i,j,k,bi,bj)*recip_drF(k)
140 & *kappaRX(i,j, k )*recip_drC( k )
141 ENDDO
142 ENDDO
143 ENDDO
144 C- 1rst upper diagonal :
145 DO k=1,Nr-1
146 DO j=jMin,jMax
147 DO i=iMin,iMax
148 d5d(i,j,k) = -deltaTLev(k)*maskC(i,j,k+1,bi,bj)
149 & *_recip_hFacC(i,j,k,bi,bj)*recip_drF(k)
150 & *KappaRX(i,j,k+1)*recip_drC(k+1)
151 ENDDO
152 ENDDO
153 ENDDO
154 C- Main diagonal :
155 DO k=1,Nr
156 DO j=jMin,jMax
157 DO i=iMin,iMax
158 c5d(i,j,k) = 1. _d 0 - b5d(i,j,k) - d5d(i,j,k)
159 ENDDO
160 ENDDO
161 ENDDO
162
163 C-- end if implicitDiffusion
164 ENDIF
165
166 IF (implicitAdvection) THEN
167
168 DO k=Nr,1,-1
169
170 C-- Compute transport
171 IF (k.EQ.Nr) THEN
172 DO j=1-Oly,sNy+Oly
173 DO i=1-Olx,sNx+Olx
174 rTransKp1(i,j) = 0.
175 ENDDO
176 ENDDO
177 ELSE
178 DO j=1-Oly,sNy+Oly
179 DO i=1-Olx,sNx+Olx
180 rTransKp1(i,j) = rTrans(i,j)
181 ENDDO
182 ENDDO
183 ENDIF
184
185 IF (k.EQ.1) THEN
186 DO j=1-Oly,sNy+Oly
187 DO i=1-Olx,sNx+Olx
188 wFld(i,j) = 0. _d 0
189 rTrans(i,j) = 0. _d 0
190 ENDDO
191 ENDDO
192 ELSE
193 DO j=1-Oly,sNy+Oly
194 DO i=1-Olx,sNx+Olx
195 wFld(i,j) = wVel(i,j,k,bi,bj)
196 rTrans(i,j) = wFld(i,j)*rA(i,j,bi,bj)*maskC(i,j,k-1,bi,bj)
197 ENDDO
198 ENDDO
199 #ifdef ALLOW_GMREDI
200 C-- Residual transp = Bolus transp + Eulerian transp
201 IF (useGMRedi)
202 & CALL GMREDI_CALC_WFLOW(
203 U wFld, rTrans,
204 I k, bi, bj, myThid )
205 #endif /* ALLOW_GMREDI */
206 ENDIF
207 DO j=jMin,jMax
208 DO i=iMin,iMax
209 c localTijk(i,j,k) = gTracer(i,j,k,bi,bj)
210 gTracer(i,j,k,bi,bj) = gTracer(i,j,k,bi,bj)
211 & + deltaTLev(1)*recip_rA(i,j,bi,bj)
212 & *_recip_hFacC(i,j,k,bi,bj)*recip_drF(k)
213 & *tracer(i,j,k,bi,bj)*(rTransKp1(i,j)-rTrans(i,j))*rkSign
214 ENDDO
215 ENDDO
216
217 #ifdef ALLOW_AIM
218 C- a hack to prevent Water-Vapor vert.transport into the stratospheric level Nr
219 IF ( K.GE.2 .AND.
220 & (.NOT.useAIM .OR.tracerIdentity.NE.GAD_SALINITY .OR.K.LT.Nr)
221 & ) THEN
222 #else
223 IF ( K.GE.2 ) THEN
224 #endif
225
226 IF ( advectionScheme.EQ.ENUM_CENTERED_2ND ) THEN
227 diagonalNumber = 3
228 CALL GAD_C2_IMPL_R( bi,bj,k, iMin,iMax,jMin,jMax,
229 I deltaTLev, rTrans,
230 U b5d, c5d, d5d,
231 I myThid )
232 ELSEIF ( advectionScheme.EQ.ENUM_UPWIND_1RST
233 & .OR. advectionScheme.EQ.ENUM_DST2 ) THEN
234 diagonalNumber = 3
235 CALL GAD_DST2U1_IMPL_R( bi,bj,k, iMin,iMax,jMin,jMax,
236 I advectionScheme, deltaTLev, rTrans,
237 U b5d, c5d, d5d,
238 I myThid )
239 ELSEIF ( advectionScheme.EQ.ENUM_FLUX_LIMIT ) THEN
240 diagonalNumber = 3
241 CALL GAD_FLUXLIMIT_IMPL_R( bi,bj,k, iMin,iMax,jMin,jMax,
242 I deltaTLev, rTrans, localTijk,
243 U b5d, c5d, d5d,
244 I myThid )
245 ELSEIF ( advectionScheme.EQ.ENUM_UPWIND_3RD
246 & .OR. advectionScheme.EQ.ENUM_CENTERED_4TH
247 & .OR. advectionScheme.EQ.ENUM_DST3 ) THEN
248 diagonalNumber = 5
249 CALL GAD_U3C4_IMPL_R( bi,bj,k, iMin,iMax,jMin,jMax,
250 I advectionScheme, deltaTLev, rTrans,
251 U a5d, b5d, c5d, d5d, e5d,
252 I myThid )
253 ELSEIF ( advectionScheme.EQ.ENUM_DST3_FLUX_LIMIT ) THEN
254 diagonalNumber = 5
255 CALL GAD_DST3FL_IMPL_R( bi,bj,k, iMin,iMax,jMin,jMax,
256 I deltaTLev, rTrans, localTijk,
257 U a5d, b5d, c5d, d5d, e5d,
258 I myThid )
259 ELSE
260 STOP 'GAD_IMPLICIT_R: Adv.Scheme in Impl form not yet coded'
261 ENDIF
262
263 ENDIF
264
265 C-- end k loop
266 ENDDO
267
268 C-- end if implicitAdvection
269 ENDIF
270
271 IF ( diagonalNumber .EQ. 3 ) THEN
272 C-- Solve tri-diagonal system :
273 CALL SOLVE_TRIDIAGONAL( iMin,iMax, jMin,jMax,
274 I b5d, c5d, d5d,
275 U gTracer,
276 O errCode,
277 I bi, bj, myThid )
278 IF (errCode.GE.1) THEN
279 STOP 'GAD_IMPLICIT_R: error when solving 3-Diag problem'
280 ENDIF
281 ELSEIF ( diagonalNumber .EQ. 5 ) THEN
282 C-- Solve penta-diagonal system :
283 CALL SOLVE_PENTADIAGONAL( iMin,iMax, jMin,jMax,
284 I a5d, b5d, c5d, d5d, e5d,
285 U gTracer,
286 O errCode,
287 I bi, bj, myThid )
288 IF (errCode.GE.1) THEN
289 STOP 'GAD_IMPLICIT_R: error when solving 5-Diag problem'
290 ENDIF
291 ELSEIF ( diagonalNumber .NE. 1 ) THEN
292 STOP 'GAD_IMPLICIT_R: no solver available'
293 ENDIF
294
295 #ifdef ALLOW_DIAGNOSTICS
296 C-- Set diagnostic suffix for the current tracer
297 IF ( useDiagnostics .AND. implicitDiffusion ) THEN
298 diagSufx = GAD_DIAG_SUFX( tracerIdentity, myThid )
299 diagName = 'DFrI'//diagSufx
300 IF ( DIAGNOSTICS_IS_ON(diagName,myThid) ) THEN
301 DO k= 1,Nr
302 IF ( k.EQ.1 ) THEN
303 C- Note: Needs to call DIAGNOSTICS_FILL at level k=1 even if array == 0
304 C otherwise counter is not incremented !!
305 DO j=1-OLy,sNy+OLy
306 DO i=1-OLx,sNx+OLx
307 df(i,j) = 0. _d 0
308 ENDDO
309 ENDDO
310 ELSE
311 DO j=1,sNy
312 DO i=1,sNx
313 df(i,j) =
314 & rA(i,j,bi,bj)
315 & * KappaRX(i,j,k)*recip_drC(k)
316 & * (gTracer(i,j,k,bi,bj) - gTracer(i,j,k-1,bi,bj))
317 ENDDO
318 ENDDO
319 ENDIF
320 CALL DIAGNOSTICS_FILL(df,diagName, k,1, 2,bi,bj, myThid)
321 ENDDO
322 ENDIF
323 ENDIF
324 #endif /* ALLOW_DIAGNOSTICS */
325
326 C-- end if Nr > 1
327 ENDIF
328
329 RETURN
330 END

  ViewVC Help
Powered by ViewVC 1.1.22