/[MITgcm]/MITgcm/pkg/thsice/thsice_advdiff.F
ViewVC logotype

Annotation of /MITgcm/pkg/thsice/thsice_advdiff.F

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


Revision 1.2 - (hide annotations) (download)
Thu Apr 5 22:06:43 2007 UTC (17 years, 1 month ago) by jmc
Branch: MAIN
Changes since 1.1: +12 -7 lines
- fix syntax for pgf
- add comments on how to get same results as when using S/R SEAICE_ADVDIFF.

1 jmc 1.2 C $Header: /u/gcmpack/MITgcm/pkg/thsice/thsice_advdiff.F,v 1.1 2007/04/04 02:40:42 jmc Exp $
2 jmc 1.1 C $Name: $
3    
4     #include "THSICE_OPTIONS.h"
5    
6     CBOP
7     C !ROUTINE: THSICE_ADVDIFF
8    
9     C !INTERFACE: ==========================================================
10     SUBROUTINE THSICE_ADVDIFF(
11     U uIce, vIce,
12     I bi, bj, myTime, myIter, myThid )
13    
14     C !DESCRIPTION: \bv
15     C *===========================================================*
16     C | SUBROUTINE THSICE_ADVDIFF
17     C | o driver for different advection routines
18     C | calls an adaption of gad_advection to call different
19     C | advection routines of pkg/generic_advdiff
20     C *===========================================================*
21     C \ev
22    
23     C !USES: ===============================================================
24     IMPLICIT NONE
25    
26     C === Global variables ===
27     C oceFWfx :: fresh water flux to the ocean [kg/m^2/s]
28     C oceSflx :: salt flux to the ocean [psu.kg/m^2/s] (~g/m^2/s)
29     C oceQnet :: heat flux to the ocean [W/m^2]
30    
31     #include "SIZE.h"
32     #include "EEPARAMS.h"
33     #include "PARAMS.h"
34     #include "GRID.h"
35     #include "GAD.h"
36     #include "THSICE_SIZE.h"
37     #include "THSICE_PARAMS.h"
38     #include "THSICE_VARS.h"
39     #include "THSICE_2DYN.h"
40    
41     C !INPUT PARAMETERS: ===================================================
42     C === Routine arguments ===
43     C uIce/vIce :: ice velocity on C-grid [m/s]
44     C bi,bj :: Tile indices
45     C myTime :: Current time in simulation (s)
46     C myIter :: Current iteration number
47     C myThid :: My Thread Id. number
48     _RL uIce (1-OLx:sNx+OLx,1-OLy:sNy+OLy)
49     _RL vIce (1-OLx:sNx+OLx,1-OLy:sNy+OLy)
50     INTEGER bi,bj
51     _RL myTime
52     INTEGER myIter
53     INTEGER myThid
54     CEndOfInterface
55    
56     #ifdef ALLOW_THSICE
57     C !LOCAL VARIABLES: ====================================================
58     C === Local variables ===
59     C i,j, :: Loop counters
60     C uTrans :: sea-ice area transport, x direction
61     C vTrans :: sea-ice area transport, y direction
62     C uTrIce :: sea-ice volume transport, x direction
63     C vTrIce :: sea-ice volume transport, y direction
64     C afx :: horizontal advective flux, x direction
65     C afy :: horizontal advective flux, y direction
66     C iceFrc :: (new) sea-ice fraction
67     C iceFld :: (new) effective sea-ice thickness
68     C iceVol :: temporary array used in advection S/R
69     C oldVol :: (old) sea-ice volume
70     C msgBuf :: Informational/error meesage buffer
71     INTEGER i, j
72     LOGICAL thSIce_multiDimAdv
73     CHARACTER*(MAX_LEN_MBUF) msgBuf
74    
75     _RL uTrans (1-OLx:sNx+OLx,1-OLy:sNy+OLy)
76     _RL vTrans (1-OLx:sNx+OLx,1-OLy:sNy+OLy)
77     _RL uTrIce (1-OLx:sNx+OLx,1-OLy:sNy+OLy)
78     _RL vTrIce (1-OLx:sNx+OLx,1-OLy:sNy+OLy)
79     _RL afx (1-OLx:sNx+OLx,1-OLy:sNy+OLy)
80     _RL afy (1-OLx:sNx+OLx,1-OLy:sNy+OLy)
81     _RS maskOce (1-OLx:sNx+OLx,1-OLy:sNy+OLy)
82     _RL iceFrc (1-OLx:sNx+OLx,1-OLy:sNy+OLy)
83     _RL iceFld (1-OLx:sNx+OLx,1-OLy:sNy+OLy)
84     _RL iceVol (1-Olx:sNx+Olx,1-Oly:sNy+Oly)
85     _RL oldVol (1-Olx:sNx+Olx,1-Oly:sNy+Oly)
86     _RL minIcHeff, minIcArea, r_minArea
87     _RL meanCellArea, areaEpsil, vol_Epsil
88 jmc 1.2 #ifdef ALLOW_DIAGNOSTICS
89     CHARACTER*8 diagName
90     CHARACTER*4 THSICE_DIAG_SUFX, diagSufx
91     EXTERNAL THSICE_DIAG_SUFX
92     #endif
93 jmc 1.1 #ifdef ALLOW_DBUG_THSICE
94     _RL tmpVar, sumVar1, sumVar2
95     #endif
96     LOGICAL dBugFlag
97     #include "THSICE_DEBUG.h"
98     CEOP
99    
100     C---+----1----+----2----+----3----+----4----+----5----+----6----+----7-|--+----|
101     C areaEpsil, vol_Epsil are 2 small numbers for ice area & ice volume:
102     C if ice area (=ice fraction * grid-cell area) or ice volume (= effective
103     C thickness * grid-cell area) are too small (i.e.: < areaEpsil,vol_Epsil)
104     C will assume that ice is gone, and will loose mass or energy.
105     C However, if areaEpsil,vol_Epsil are much smaller than minimun ice area
106     C (iceMaskMin*rAc) and minimum ice volume (iceMaskMin*himin*rAc),
107     C good chance that this will never happen within 1 time step.
108    
109     dBugFlag = debugLevel.GE.debLevB
110    
111     C- definitively not an accurate computation of mean grid-cell area;
112     C but what matter here is just to have the right order of magnitude.
113     meanCellArea = Nx*Ny
114     meanCellArea = globalArea / meanCellArea
115     areaEpsil = 1. _d -10 * meanCellArea
116     vol_Epsil = 1. _d -15 * meanCellArea
117    
118     minIcArea = iceMaskMin
119     minIcHeff = iceMaskMin*himin
120     r_minArea = 0. _d 0
121     IF ( minIcArea.GT.0. _d 0 ) r_minArea = 1. _d 0 / minIcArea
122    
123     thSIce_multiDimAdv = .TRUE.
124     IF ( thSIceAdvScheme.EQ.ENUM_CENTERED_2ND
125     & .OR.thSIceAdvScheme.EQ.ENUM_UPWIND_3RD
126     & .OR.thSIceAdvScheme.EQ.ENUM_CENTERED_4TH ) THEN
127     thSIce_multiDimAdv = .FALSE.
128     ENDIF
129    
130     C-- Initialisation (+ build oceanic mask)
131     DO j=1-OLy,sNy+OLy
132     DO i=1-OLx,sNx+OLx
133     maskOce(i,j) = 0. _d 0
134     IF ( hOceMxL(i,j,bi,bj).GT.0. ) maskOce(i,j) = 1.
135     iceVol(i,j) = 0. _d 0
136     uTrans(i,j) = 0. _d 0
137     vTrans(i,j) = 0. _d 0
138     uTrIce(i,j) = 0. _d 0
139     vTrIce(i,j) = 0. _d 0
140     oceFWfx(i,j,bi,bj) = 0. _d 0
141     oceSflx(i,j,bi,bj) = 0. _d 0
142     oceQnet(i,j,bi,bj) = 0. _d 0
143     ENDDO
144     ENDDO
145    
146     IF ( thSIce_diffK .GT. 0. ) THEN
147     CALL THSICE_DIFFUSION(
148     I maskOce,
149     U uIce, vIce,
150     I bi, bj, myTime, myIter, myThid )
151     ENDIF
152    
153     IF ( thSIce_multiDimAdv ) THEN
154    
155     C- Calculate ice transports through tracer cell faces.
156     DO j=1-Oly,sNy+Oly
157     DO i=1-Olx+1,sNx+Olx
158     uTrIce(i,j) = uIce(i,j)*_dyG(i,j,bi,bj)
159     & *maskOce(i-1,j)*maskOce(i,j)
160     ENDDO
161     ENDDO
162     DO j=1-Oly+1,sNy+Oly
163     DO i=1-Olx,sNx+Olx
164     vTrIce(i,j) = vIce(i,j)*_dxG(i,j,bi,bj)
165     & *maskOce(i,j-1)*maskOce(i,j)
166     ENDDO
167     ENDDO
168    
169     C-- Fractional area
170     DO j=1-Oly,sNy+Oly
171     DO i=1-Olx,sNx+Olx
172     iceFrc(i,j) = iceMask(i,j,bi,bj)
173     ENDDO
174     ENDDO
175     CALL THSICE_ADVECTION(
176     I GAD_SI_FRAC, thSIceAdvScheme, .TRUE.,
177     I uTrIce, vTrIce, maskOce, thSIce_deltaT, areaEpsil,
178     U iceVol, iceFrc,
179     O uTrans, vTrans,
180     I bi, bj, myTime, myIter, myThid )
181    
182     C-- Snow thickness
183     DO j=1-Oly,sNy+Oly
184     DO i=1-Olx,sNx+Olx
185     iceVol(i,j) = iceMask(i,j,bi,bj)*rA(i,j,bi,bj)
186     ENDDO
187     ENDDO
188     CALL THSICE_ADVECTION(
189     I GAD_SI_HSNOW, thSIceAdvScheme, .FALSE.,
190     I uTrans, vTrans, maskOce, thSIce_deltaT, areaEpsil,
191     U iceVol, snowHeight(1-Olx,1-Oly,bi,bj),
192     O afx, afy,
193     I bi, bj, myTime, myIter, myThid )
194    
195     C-- sea-ice Thickness
196     DO j=1-Oly,sNy+Oly
197     DO i=1-Olx,sNx+Olx
198     iceVol(i,j) = iceMask(i,j,bi,bj)*rA(i,j,bi,bj)
199     oldVol(i,j) = iceVol(i,j)*iceHeight(i,j,bi,bj)
200     ENDDO
201     ENDDO
202     CALL THSICE_ADVECTION(
203     I GAD_SI_HICE, thSIceAdvScheme, .FALSE.,
204     I uTrans, vTrans, maskOce, thSIce_deltaT, areaEpsil,
205     U iceVol, iceHeight(1-Olx,1-Oly,bi,bj),
206     O uTrIce, vTrIce,
207     I bi, bj, myTime, myIter, myThid )
208     #ifdef ALLOW_DBUG_THSICE
209     IF ( dBugFlag ) THEN
210     sumVar1 = 0.
211     sumVar2 = 0.
212     DO j=1,sNy
213     DO i=1,sNx
214     C- Check that updated iceVol = iceFrc*rA
215     tmpVar = ABS(iceVol(i,j)-iceFrc(i,j)*rA(i,j,bi,bj))
216     IF ( tmpVar.GT.0. ) THEN
217     sumVar1 = sumVar1 + 1.
218     sumVar2 = sumVar2 + tmpVar
219     ENDIF
220     IF ( tmpVar.GT.vol_Epsil ) THEN
221     WRITE(6,'(A,2I4,2I2,I12)') 'ARE_ADV: ij,bij,it=',
222     & i,j,bi,bj,myIter
223     WRITE(6,'(2(A,1P2E14.6))') 'ARE_ADV: iceVol,iceFrc*rA=',
224     & iceVol(i,j),iceFrc(i,j)*rA(i,j,bi,bj),
225     & ' , diff=', tmpVar
226     ENDIF
227     IF ( dBug(i,j,bi,bj) ) THEN
228     WRITE(6,'(A,2I4,2I2,I12)') 'ICE_ADV: ij,bij,it=',
229     & i,j,bi,bj,myIter
230     WRITE(6,'(2(A,1P2E14.6))')
231     & 'ICE_ADV: uIce=', uIce(i,j), uIce(i+1,j),
232     & ' , vIce=', vIce(i,j), vIce(i,j+1)
233     WRITE(6,'(2(A,1P2E14.6))')
234     c & 'ICE_ADV: heff_b,a=', HEFF(i,j,2,bi,bj),HEFF(i,j,1,bi,bj)
235     c WRITE(6,'(A,1P4E14.6)') 'ICE_ADV: mFx=', gFld(i,j)
236     ENDIF
237     ENDDO
238     ENDDO
239     IF ( sumVar2.GT.vol_Epsil )
240     & WRITE(6,'(A,2I2,I10,A,I4,1P2E14.6)') 'ARE_ADV: bij,it:',
241     & bi,bj,myIter, ' ; Npts,aveDiff,Epsil=',
242     & INT(sumVar1),sumVar2/sumVar1,vol_Epsil
243     ENDIF
244     #endif
245     #ifdef ALLOW_DIAGNOSTICS
246     C-- Diagnosse advective fluxes (ice-fraction, snow & ice thickness):
247     IF ( useDiagnostics ) THEN
248     diagSufx = THSICE_DIAG_SUFX( GAD_SI_FRAC, myThid )
249     diagName = 'ADVx'//diagSufx
250     CALL DIAGNOSTICS_FILL( uTrans, diagName, 1,1,2,bi,bj, myThid )
251     diagName = 'ADVy'//diagSufx
252     CALL DIAGNOSTICS_FILL( vTrans, diagName, 1,1,2,bi,bj, myThid )
253    
254     diagSufx = THSICE_DIAG_SUFX( GAD_SI_HSNOW, myThid )
255     diagName = 'ADVx'//diagSufx
256     CALL DIAGNOSTICS_FILL( afx, diagName, 1,1,2,bi,bj, myThid )
257     diagName = 'ADVy'//diagSufx
258     CALL DIAGNOSTICS_FILL( afy, diagName, 1,1,2,bi,bj, myThid )
259    
260     diagSufx = THSICE_DIAG_SUFX( GAD_SI_HICE, myThid )
261     diagName = 'ADVx'//diagSufx
262     CALL DIAGNOSTICS_FILL( uTrIce, diagName, 1,1,2,bi,bj, myThid )
263     diagName = 'ADVy'//diagSufx
264     CALL DIAGNOSTICS_FILL( vTrIce, diagName, 1,1,2,bi,bj, myThid )
265     ENDIF
266     #endif
267    
268     C-- Enthalpy in layer 1
269     DO j=1-Oly,sNy+Oly
270     DO i=1-Olx,sNx+Olx
271     iceVol(i,j) = oldVol(i,j)
272     ENDDO
273     ENDDO
274     CALL THSICE_ADVECTION(
275     I GAD_SI_QICE1, thSIceAdvScheme, .FALSE.,
276     I uTrIce, vTrIce, maskOce, thSIce_deltaT, vol_Epsil,
277     U iceVol, Qice1(1-Olx,1-Oly,bi,bj),
278     O afx, afy,
279     I bi, bj, myTime, myIter, myThid )
280     #ifdef ALLOW_DBUG_THSICE
281     IF ( dBugFlag ) THEN
282     DO j=1,sNy
283     DO i=1,sNx
284     IF ( dBug(i,j,bi,bj) ) THEN
285     c WRITE(6,'(A,1P4E14.6)') 'ICE_ADV: Qice1_b,a=',
286     c & Qice1(i,j,bi,bj),
287     c & ( iceFld(i,j) + thSIce_deltaT * gFld(i,j)
288     c & ) * recip_heff(i,j)
289     c WRITE(6,'(A,1P4E14.6)') 'ICE_ADV: q1Fx=', gFld(i,j)
290     ENDIF
291     ENDDO
292     ENDDO
293     ENDIF
294     #endif
295     #ifdef ALLOW_DIAGNOSTICS
296     IF ( useDiagnostics ) THEN
297     diagSufx = THSICE_DIAG_SUFX( GAD_SI_QICE1, myThid )
298     diagName = 'ADVx'//diagSufx
299     CALL DIAGNOSTICS_FILL( afx, diagName, 1,1,2,bi,bj, myThid )
300     diagName = 'ADVy'//diagSufx
301     CALL DIAGNOSTICS_FILL( afy, diagName, 1,1,2,bi,bj, myThid )
302     ENDIF
303     #endif
304    
305     C-- Enthalpy in layer 2
306     DO j=1-Oly,sNy+Oly
307     DO i=1-Olx,sNx+Olx
308     iceVol(i,j) = oldVol(i,j)
309     ENDDO
310     ENDDO
311     CALL THSICE_ADVECTION(
312     I GAD_SI_QICE2, thSIceAdvScheme, .FALSE.,
313     I uTrIce, vTrIce, maskOce, thSIce_deltaT, vol_Epsil,
314     U iceVol, Qice2(1-Olx,1-Oly,bi,bj),
315     O afx, afy,
316     I bi, bj, myTime, myIter, myThid )
317     #ifdef ALLOW_DBUG_THSICE
318     IF ( dBugFlag ) THEN
319     sumVar1 = 0.
320     sumVar2 = 0.
321     DO j=1,sNy
322     DO i=1,sNx
323     C- Check that updated iceVol = Hic*Frc*rA
324     tmpVar = ABS(iceVol(i,j)
325     & -iceHeight(i,j,bi,bj)*iceFrc(i,j)*rA(i,j,bi,bj))
326     IF ( tmpVar.GT.0. ) THEN
327     sumVar1 = sumVar1 + 1.
328     sumVar2 = sumVar2 + tmpVar
329     ENDIF
330     IF ( tmpVar.GT.vol_Epsil ) THEN
331     WRITE(6,'(A,2I4,2I2,I12)') 'VOL_ADV: ij,bij,it=',
332     & i,j,bi,bj,myIter
333     WRITE(6,'(2(A,1P2E14.6))') 'VOL_ADV: iceVol,Hic*Frc*rA=',
334     & iceVol(i,j),iceHeight(i,j,bi,bj)*iceFrc(i,j)*rA(i,j,bi,bj),
335     & ' , diff=', tmpVar
336     ENDIF
337     IF ( dBug(i,j,bi,bj) ) THEN
338     c WRITE(6,'(A,1P4E14.6)') 'ICE_ADV: Qice2_b,a=',
339     c & Qice2(i,j,bi,bj),
340     c & ( iceFld(i,j) + thSIce_deltaT * gFld(i,j)
341     c & ) * recip_heff(i,j)
342     c WRITE(6,'(A,1P4E14.6)') 'ICE_ADV: q2Fx=', gFld(i,j)
343     ENDIF
344     ENDDO
345     ENDDO
346     IF ( sumVar2.GT.vol_Epsil )
347     & WRITE(6,'(A,2I2,I10,A,I4,1P2E14.6)') 'VOL_ADV: bij,it:',
348     & bi,bj,myIter, ' ; Npts,aveDiff,Epsil=',
349     & INT(sumVar1),sumVar2/sumVar1,vol_Epsil
350     ENDIF
351     #endif
352     #ifdef ALLOW_DIAGNOSTICS
353     IF ( useDiagnostics ) THEN
354     diagSufx = THSICE_DIAG_SUFX( GAD_SI_QICE2, myThid )
355     diagName = 'ADVx'//diagSufx
356     CALL DIAGNOSTICS_FILL( afx, diagName, 1,1,2,bi,bj, myThid )
357     diagName = 'ADVy'//diagSufx
358     CALL DIAGNOSTICS_FILL( afy, diagName, 1,1,2,bi,bj, myThid )
359     ENDIF
360     #endif
361    
362     C-- Update Ice Fraction, Ice thickness and snow thickness:
363     C and adjust sea-ice state if not enough ice.
364     DO j=1,sNy
365     DO i=1,sNx
366     C- store new effective ice-thickness
367     iceFld(i,j) = iceHeight(i,j,bi,bj)*iceFrc(i,j)
368     IF ( iceFld(i,j) .GE. minIcHeff ) THEN
369     C- where there is enough ice, ensure that Ice fraction is > minIcArea & < 1
370     IF ( iceFrc(i,j) .GT. 1. _d 0 ) THEN
371     iceMask(i,j,bi,bj) = 1. _d 0
372     iceHeight(i,j,bi,bj) = iceFld(i,j)
373     snowHeight(i,j,bi,bj) = snowHeight(i,j,bi,bj)*iceFrc(i,j)
374     ELSEIF ( iceFrc(i,j) .LT. minIcArea ) THEN
375     iceMask(i,j,bi,bj) = minIcArea
376     iceHeight(i,j,bi,bj) = iceFld(i,j)*r_minArea
377     snowHeight(i,j,bi,bj) = snowHeight(i,j,bi,bj)
378     & *iceFrc(i,j)*r_minArea
379     ELSE
380     iceMask(i,j,bi,bj) = iceFrc(i,j)
381     ENDIF
382     ELSE
383 jmc 1.2 C- Not enough ice, melt the tiny amount of snow & ice:
384 jmc 1.1 C and return frsh-water, salt & energy to the ocean (flx > 0 = into ocean)
385 jmc 1.2 C- - Note: using 1rst.Order Upwind, I can get the same results as when
386     C using seaice_advdiff (with SEAICEadvScheme=1) providing I comment
387     C out the following lines (and then loose conservation).
388     C- -
389 jmc 1.1 oceFWfx(i,j,bi,bj) = ( rhos*snowHeight(i,j,bi,bj)
390     & +rhoi*iceHeight(i,j,bi,bj) )
391     & *iceFrc(i,j)/thSIce_deltaT
392     oceSflx(i,j,bi,bj) =saltice*rhoi*iceFld(i,j)/thSIce_deltaT
393     oceQnet(i,j,bi,bj) = -qsnow*rhos*snowHeight(i,j,bi,bj)
394     & *iceFrc(i,j)/thSIce_deltaT
395     & -( Qice1(i,j,bi,bj)
396     & +Qice2(i,j,bi,bj) )*0.5 _d 0
397     & *rhoi*iceFld(i,j)/thSIce_deltaT
398 jmc 1.2 C- -
399 jmc 1.1 c flx2oc (i,j) = flx2oc (i,j) +
400     c frw2oc (i,j) = frw2oc (i,j) +
401     c fsalt (i,j) = fsalt (i,j) +
402     iceMask (i,j,bi,bj) = 0. _d 0
403     iceHeight (i,j,bi,bj) = 0. _d 0
404     snowHeight(i,j,bi,bj) = 0. _d 0
405     Qice1 (i,j,bi,bj) = 0. _d 0
406     Qice2 (i,j,bi,bj) = 0. _d 0
407     snowAge (i,j,bi,bj) = 0. _d 0
408     ENDIF
409     ENDDO
410     ENDDO
411    
412     #ifdef ALLOW_DBUG_THSICE
413     IF ( dBugFlag ) THEN
414     DO j=1,sNy
415     DO i=1,sNx
416     IF ( dBug(i,j,bi,bj) ) THEN
417     WRITE(6,'(2(A,1P2E14.6))')
418     c & 'ICE_ADV: area_b,a=', AREA(i,j,2,bi,bj),AREA(i,j,1,bi,bj)
419     c WRITE(6,'(A,1P4E14.6)') 'ICE_ADV: mFx=', gFld(i,j)
420     ENDIF
421     ENDDO
422     ENDDO
423     ENDIF
424     #endif
425    
426     ELSE
427     C--- if not multiDimAdvection
428    
429     WRITE(msgBuf,'(2A)') 'S/R THSICE_ADVDIFF: ',
430     & 'traditional advection/diffusion not yet implemented'
431     CALL PRINT_ERROR( msgBuf , myThid)
432     WRITE(msgBuf,'(2A)') ' ',
433     & 'for ThSice variable Qice1, Qice2, SnowHeight. Sorry!'
434     CALL PRINT_ERROR( msgBuf , myThid)
435     STOP 'ABNORMAL: END: S/R THSICE_ADVDIFF'
436    
437     C--- end if multiDimAdvection
438     ENDIF
439    
440     #endif /* ALLOW_THSICE */
441    
442     RETURN
443     END

  ViewVC Help
Powered by ViewVC 1.1.22